1
votes

Comment résoudre le problème que le programme fonctionne de la même manière en cas de nombres négatifs?

En conséquence, le programme doit afficher les 3 plus grands éléments de la séquence. Les éléments doivent être affichés de petit à grand et ne pas utiliser de tableau ...

Exemples

Entrée:

#include <iostream>

int main() {
  int n;
  std::cin >> n;
  int number;
  std::cin >> number;
  int max1, max2, max3;
  max1 = max2 = max3 = number;
  for (int i = 1; i < n; i++) {
    std::cin >> number;
    if (number > max3) {
      if (number > max2) {
        if (number > max1) {
          max3 = max2;
          max2 = max1;
          max1 = number;
        } else {
          max2 = number;
        }
      } else {
        max3 = number;
      }
    }
  }
  std::cout << max3 << " " << max2 << " " << max1;
}

Résultat du travail:

-2 -1 0

Entrée:

3 0 -1 -2

Résultat du travail:

2 15 16

Entrée:

5 2 -4 16 0 15

Résultat du travail:

1 2 3

Voici mon code:

3 1 2 3

5 commentaires

⟼N'oubliez pas qu'il est toujours important, en particulier lorsque vous apprenez et posez des questions sur Stack Overflow, de garder votre code aussi organisé que possible. Indentation cohérente aide à communiquer la structure et, surtout, l'intention, ce qui nous aide à naviguer rapidement à la racine de le problème sans passer beaucoup de temps à essayer de décoder ce qui se passe.


Pourquoi ne pas utiliser std :: vector et std :: sort ici? Qu'est-ce qui serait également différent avec les nombres négatifs?


Quel est le but du code? Quel résultat obtenez-vous avec des nombres négatifs par rapport à ce que vous attendez?


Voir l ' exemple minimal reproductible ... veuillez ajouter le résultat attendu pour chaque entrée.


Quelle est la question?


4 Réponses :


0
votes
int main () {
           int n;
           std::cin >> n;
           int number;
           std::cin >> number;
           int max1, max2, max3;
           max1 = max2 = max3 =number;
           for(int i = 1; i < n; i++) {
           std::cin >> number;
           if (number > max3) {
           if (number > max2) {
           if (number > max1) {
               max3 = max2; 
               max2 = max1;
               max1 = number;
               } else {
               max3 = max2;
               max2 = number;
               }
               } else {
               max3 = number;
               }
               }
               }
               std::cout << max3 << " " << max2 << " " << max1;  
               }
If the number is greater than max2 but smaller than max1 then max2 is the new max3 and max2 is number, that was the mistake.

4 commentaires

C'est une erreur. Il y en a plus.


quand on saisit des nombres -> 3 0 -1 -2 le programme donne: 0 0 0 mais doit donner: -2 -1 0


Oui, car les valeurs maximales commencent toutes au premier nombre - 0. Toutes les valeurs négatives sont inférieures à cela.


J'ai besoin du programme return -2 -1 0 comment faire ça ???



0
votes

N'écrivez pas tout dans main . Découpez le code en morceaux plus petits pour le rendre plus facile à lire.

Voici un exemple (un peu compliqué):

class AccumulateTopThree
{
public:
    void update(int x)
    {
        if (!isUnique(x)) return;
        keepInOrder(c, x);
        keepInOrder(b, c);
        keepInOrder(a, b);
    }

    void print(std::ostream& out)
    {
        // TODO: handle case when count of input nubers is less then 3
        out << c << ' ' << b << ' ' << a << '\n';
    }

private:
    bool isUnique(int x) const
    {
        return a != x && b != x && c != x;
    }

    static void keepInOrder(int &a, int &b)
    {
        if (a < b) std::swap(a, b);
    }

private:
    int a = std::numeric_limits<int>::min();
    int b = a;
    int c = a;
};

https://wandbox.org/permlink/OFkQUaGI9PygAV6D


4 commentaires

J'ai besoin de résoudre le problème de manière simple ... par exemple tout écrire dans main @Marek R


tout dans main n'est pas une manière plus simple.


J'apprends juste le C ++, c'est pourquoi j'ai besoin de solutions simples))


Juste pour être clair, j'ai fait cela un peu plus de fantaisie que ce dont vous avez besoin exprès. De cette façon, j'évite de donner une solution complète. Si vous faites un effort, vous pouvez supprimer la classe et avoir un bon code.



1
votes

Mes cinq cents.:)

16 15 5 

Si vous entrez

6
5 2 -4 16 0 15

alors la sortie est

#include <iostream>
#include <set>
#include <iterator>
#include <algorithm>

int main() 
{
    size_t n = 0;

    std::set<int> set;

    std::cin >> n;

    std::copy_n( std::istream_iterator<int>( std::cin ), n, 
                 std::inserter( set, std::end( set ) ) );

    size_t i = 3;

    for ( auto it = std::rbegin( set ); i-- != 0 && it != std::rend( set ); ++it )
    {
        std::cout << *it << ' ';
    }
    std::cout << '\n';

    return 0;
}

Si vous devez entrer

-1

alors la sortie est

5
-1 -1 -1 -1 -1

Ou si vous devez entrer p>

#include <iostream>
#include <utility>

int main() 
{
    size_t n = 0;
    int max1, max2, max3;

    std::cin >> n;

    size_t i = 0;
    for ( int number; n-- && std::cin >> number;  )
    {
        if ( i == 0 )
        {
            max3 = number;
            i = 1;
        }
        else
        {
            if ( max3 < number )
            {
                std::swap( max3, number );
            }

            if ( number < max3 )
            {
                if ( i == 1 )
                {
                    max2 = number;
                    i = 2;
                }                   
                else
                {
                    if ( max2 < number )
                    {
                        std::swap( max2, number );
                    }

                    if ( number < max2 )
                    {
                        if ( i == 2 || max1 < number )
                        {
                            max1 = number;
                            i = 3;
                        }       
                    }
                }
            }               
        }           
    }

    if ( i > 0 )
    {
        std::cout << max3;
    }
    if ( i > 1 )
    {
        std::cout << ", " << max2;
    }
    if ( i > 2 )
    {
        std::cout << ", " << max1;
    }

    std::cout << '\n';

    return 0;
}

alors la sortie du programme est

3, 0, -1

Faites attention à ce qu'en général l'utilisateur peut saisir moins de 3 nombres. :)

La solution ci-dessus autorise les valeurs maximales dupliquées.

S'il est nécessaire que les valeurs maximales ne soient pas répétées, le programme peut ressembler à ceci.

4
3 0 -1 -2

Par exemple, si vous devez entrer

4, 0, -2

où tous les nombres sont égaux, le résultat contiendra un nombre maximum maximum

6
-5 -2 4 -16 0 -15

Si vous utilisez des conteneurs standard, le conteneur standard std :: set est le conteneur le plus approprié.

Par exemple

16, 15, 5

Si vous devez entrer

6
5 2 -4 16 0 15

alors la sortie est

#include <iostream>
#include <utility>

int main() 
{
    size_t n = 0;
    int max1, max2, max3;

    std::cin >> n;

    size_t i = 0;
    for ( int number; n-- && std::cin >> number;  i = i < 3 ? i + 1 : i  )
    {
        if ( i == 0 )
        {
            max3 = number;
        }
        else
        {
            if ( max3 < number )
            {
                std::swap( max3, number );
            }

            if ( i == 1 )
            {
                max2 = number;
            }
            else
            {
                if ( max2 < number )
                {
                    std::swap( max2, number );
                }

                if ( i == 2 || max1 < number )
                {
                    max1 = number;
                }       
            }
        }           
    }

    if ( i > 0 )
    {
        std::cout << max3;
    }
    if ( i > 1 )
    {
        std::cout << ", " << max2;
    }
    if ( i > 2 )
    {
        std::cout << ", " << max1;
    }

    std::cout << '\n';

    return 0;
}


1 commentaires

Vlad de Moscou merci beaucoup! Votre première option était ce dont j'avais besoin



1
votes

J'utiliserais des algorithmes standard pour que les choses restent aussi simples que possible.

#include <algorithm>
#include <iostream>
#include <iterator>
#include <vector>

int main() {
    std::vector<std::vector<int>> tests{
        {5, 2, -4, 16, 0, 15},
        {3, 0, -1, -2}
    };
    for(auto& test : tests) {
        // calculate how many elements to show, 0-3
        auto elems = std::min(test.size(), static_cast<size_t>(3)); 

        // sort "elems" elements in decending order
        std::partial_sort(
            test.begin(),
            std::next(test.begin(), elems),
            test.end(),
            std::greater<>()
        );

        // copy the result to std::out, in reverse order since they are sorted "backwards"
        std::copy(
            std::prev(test.crend(), elems),
            test.crend(),
            std::ostream_iterator<int>(std::cout, " ")
        );
        std::cout << '\n';
    }
}

Résultat:

5 15 16 
-1 0 3

Un peu Une manière plus compliquée consiste à trier partiellement le vecteur. Cela le rend plus efficace car vous n'avez besoin que de 3 éléments triés.

std :: partial_sort met les plus petits éléments en premier, nous devons donc les trier par ordre décroissant (en utilisant std :: supérieur ).

#include <algorithm>
#include <iostream>
#include <iterator>
#include <vector>

int main() {
    std::vector<std::vector<int>> tests{
        {5, 2, -4, 16, 0, 15},
        {3, 0, -1, -2}
    };
    for(auto& test : tests) {
        // sort the vector to get the three largest last
        std::sort(test.begin(), test.end());

        // create an iterator 3 steps back from the end
        // (or less if the vector doesn't have 3 elements)
        auto first = std::prev(test.cend(), std::min(test.size(), static_cast<size_t>(3)));

        // copy to std::cout
        std::copy(first, test.cend(), std::ostream_iterator<int>(std::cout, " "));
        std::cout << '\n';
    }
}


2 commentaires

Vous pouvez utiliser std :: partial_sort pour ne pas avoir à trier le tout.


@BessieTheCow Je suis d'accord. Ce serait plus efficace - mais je ne voulais pas le compliquer. Je l'ai cependant ajouté en option maintenant.