1
votes

Aucune sortie affichée sur le problème 8 du projet euler

Il s'agit du problème 8 du projet euler .

Je ne comprends pas pourquoi aucune sortie est montré. Veuillez ne pas écrire de solution directe, je ne veux juste pas savoir où ma logique est erronée.

    #include <stdio.h>

int main() {
    //code

    char a[1001]='7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450';

    int p,i=0,m;
    for(p=1;i<13;i++)p=p*((int)a[i]-48);m=p;printf("%d %d\n",m,p);
    for(;i<1001&&a[i]!='\0';i++)
    {
        p=p/((int)(a[i-13]-48));
        p=p*((int)(a[i]-48));
        if(m<p)m=p;
    }
    printf("%d\n",m);
    return 0;
}

c

6 commentaires

Veuillez reformater la question pour inclure la description du résultat souhaité, et le lien vers le projet Euler doit être dans le corps, de sorte qu'il soit cliquable.


Utiliser des guillemets simples '' pour l'initialisation de a n'a aucun sens. Vous devriez obtenir des avertissements ou des erreurs du compilateur pour cela. Sinon, veuillez vérifier les paramètres de votre compilateur.


Notez que pour obtenir le produit de 13 chiffres simples, vous aurez besoin d'une variable avec une plage plus grande qu'un int 32 bits. Par exemple 9 ^ 13 = 2541865828329.


Une chaîne littérale doit être placée entre guillemets doubles " et non entre guillemets simples '.


Veuillez éditer la source pour la rendre un peu plus lisible ... :)


Une sortie est affichée, alors que demandez-vous du tout? (bien sûr, après avoir corrigé le '7316717653 ...' -> "7316717653 ..." dans la chaîne)


4 Réponses :


4
votes

Vous avez des guillemets erronés dans l'initialiseur de char a [1001] - les guillemets simples sont pour une constante de caractère , utilisez des guillemets doubles pour un littéral de chaîne < / em>. Et obtenez un meilleur environnement de compilation - un qui prévient de telles erreurs.

Ensuite, l'idée de supprimer le treizième-dernier facteur du produit actuel semble astucieuse à première vue, mais elle casse si le chiffre est zéro et que vous essayez de diviser par lui.


1 commentaires

merci d'avoir répondu, je n'ai vraiment pas remarqué les 0 et je ne connaissais pas les guillemets simples et doubles, je pensais que n'importe quelle citation pouvait être utilisée comme en python.



3
votes

vous devez changer char a [1001] = '123'; en char a [] = "123"; puis exécutez-le. voici le code XXX

output -:
7 7
21 21                                                                                                                          
126 126                                                                                                                        
882 882                                                                                                                        
882 882                                                                                                                        
6174 6174  
37044 37044                                                                                                                    
185220 185220                                                                                                                  
555660 555660                                                                                                                  
555660 555660 
5000940 5000940                                                                                                                
5000940 


0 commentaires

4
votes

Il y a quelques erreurs dans le code affiché, à la fois syntaxique et logique.

Comme déjà noté, vous devriez utiliser des guillemets doubles pour la chaîne littérale. Vous pouvez également l'écrire divisé en différentes lignes, le compilateur concaténera tous les morceaux et ajoutera le terminateur \ 0 .

#define MAX_ADJACENT_DIGITS 13
// ...
long long product = 0, max_product = 0;
int n_digits = 0;

Le type int est peut-être trop petit pour représenter la valeur du produit. Le Standard garantit seulement qu'il est capable de représenter des nombres jusqu'à 32767 et même un int 32 bits (courant de nos jours) ne peut pas stocker 9 13 . Je suggère d'utiliser un long long et des noms plus significatifs, par exemple:

const char *digits = "73167176531330624919225119674426574742355349194934"
                      // ...
                     "71636269561882670428252483600823257530420752963450";

L'erreur dans votre algorithme est qu'il ne tient pas compte de ce se produit lorsqu'un chiffre est égal à zéro. Une division entière par zéro pourrait conduire à une erreur d'exécution, et en plus de cela, tous les produits des chiffres proches sont égaux à zéro.

Considérez cette version modifiée:

  • Pour chaque caractère de la chaîne, du premier à celui qui est égal à '\0'

    • S'il est égal à '0' (notez les guillemets simples et l'utilisation du caractère réel, pas un nombre "magique")

      • réinitialisez le produit et n_digits .
      • Ignorer le reste du corps de la boucle ( continue; ).
    • S'il s'agit du premier chiffre d'un groupe de chiffres adjacents ( n_digits == 0 )

      • que produit est égal à ce chiffre et nous pouvons augmenter n_digits .
      • Continuez avec le chiffre suivant.
    • Ici, nous pouvons mettre à jour le produit ( produit * = chiffres [i] - '0'; ) et augmenter n_digits .

      li>
    • Si nous avons dépassé le nombre maximum de chiffres adjacents

      • supprimez le plus ancien ( produit / = chiffres [i - MAX_ADJACENT_DIGITS] - '0'; ) du produit et réinitialisez n_digits au maximum. li >
      • Mettez à jour la valeur maximale des produits, si le produit actuel est plus grand.

En suivant ces étapes, votre programme devrait trouver la sous-séquence de chiffres "5576689664895" et afficher son produit.


7 commentaires

Je comprends où je me suis trompé et je me sens stupide de ne pas avoir remarqué ces zéros. merci pour votre réponse, cela a vraiment aidé


Mieux vaut diviser la chaîne en sous-chaînes de 13 caractères ou plus, séparées par des chiffres 0 ... non? car tout chiffre 0 produira un résultat nul. Les séquences plus courtes doivent être ignorées (car elles produisent un résultat nul) et les plus longues ou égales sont les seules à prendre en compte (elles n'ont pas du tout de chiffres 0 )


@LuisColorado Si vous suggérez de retarder l'évaluation des produits jusqu'à ce qu'une sous-chaîne suffisamment longue de chiffres différents de zéro soit trouvée, cela semble être une bonne idée. Cela ne semble cependant pas avoir beaucoup d'impact dans ce cas particulier: 1 ou 2 , mais je suis sûr que vous pouvez fournir une meilleure implémentation.


J'ai écrit une solution à cela et cela fonctionne très bien ... Comme l'OP a demandé de ne pas publier de solution de travail, j'ai décidé de ne pas l'inclure dans une réponse.


Il est curieux de trouver des séquences de moins de 13 caractères qui se terminent par des produits plus grands que l'approche de 13 caractères. Je n'ai pas vérifié les traces verbeuses dans mon programme, mais il doit s'agir de séquences entourées de caractères 0 .


@LuisColorado Nice. Cela ne semble pas être le cas, avec la chaîne d'entrée donnée. Pensez-vous à un algorithme particulier (mémorisation?) Ou à une approche "force brute" (il suffit de changer le nombre maximum de chiffres)?


@Bob__, j'ai fait un bug en sélectionnant un entier 32 bits pour le produit .... J'ai changé cela dans mon référentiel de solutions de github. (également dans ma réponse à cette question)



3
votes

Voici mon approche de la solution d'euler # 8. Il utilise d'abord la fonction stroke (3) pour séparer la chaîne complète en morceaux séparés par des caractères 0 . Ensuite, il fait glisser une fenêtre de longueur n sur les chaînes séparées (les chaînes de longueur inférieure à n ne peuvent pas obtenir suffisamment de chiffres pour former un produit sans impliquer un 0 code> afin qu'ils soient rejetés.

Nous construisons ensuite le premier produit en multipliant le premier ensemble de n chiffres. Une fois défini, la fenêtre est découpée en multipliant le produit par le chiffre suivant et en divisant le produit par le dernier chiffre d'une file d'attente, pointé par p et q . Les produits sont comparés au maximum et dans le cas où ils sont plus grands, la position de la correspondance et la nouvelle valeur du produit sont stockées.

À la fin, la sous-chaîne est imprimée, en commençant à la position stockée, l'index est imprimé et le produit.

Le programme accepte les options -n et -v:

  • -n nombre permet de spécifier un nombre différent (par défaut à 13, comme l'indique euler # 8)
  • -v produit plus de sortie, indiquant à chaque étape la chaîne à tester et les produits impliqués.

Pour compiler le programme, il suffit de:

#include <getopt.h>
#include <stdio.h>
#include <string.h>

#define FLAG_VERBOSE    (1 << 0)

int flags = 0;

int n = 13;
char N[] = 
                "73167176531330624919225119674426574742355349194934"
                "96983520312774506326239578318016984801869478851843"
                "85861560789112949495459501737958331952853208805511"
                "12540698747158523863050715693290963295227443043557"
                "66896648950445244523161731856403098711121722383113"
                "62229893423380308135336276614282806444486645238749"
                "30358907296290491560440772390713810515859307960866"
                "70172427121883998797908792274921901699720888093776"
                "65727333001053367881220235421809751254540594752243"
                "52584907711670556013604839586446706324415722155397"
                "53697817977846174064955149290862569321978468622482"
                "83972241375657056057490261407972968652414535100474"
                "82166370484403199890008895243450658541227588666881"
                "16427171479924442928230863465674813919123162824586"
                "17866458359124566529476545682848912883142607690042"
                "24219022671055626321111109370544217506941658960408"
                "07198403850962455444362981230987879927244284909188"
                "84580156166097919133875499200524063689912560717606"
                "05886116467109405077541002256983155200055935729725"
                "71636269561882670428252483600823257530420752963450";

int main(int argc, char **argv)
{
    int opt;
    while ((opt = getopt(argc, argv, "n:v")) != EOF) {
        switch (opt) {
        case 'n':
            if (sscanf(optarg, "%d", &n) != 1) {
                fprintf(stderr,
                        "invalid number: %s\n",
                        optarg);
            }
            break;
        case 'v':
            flags |= FLAG_VERBOSE;
            break;
        } /* switch */
    } /* while */

    if (flags & FLAG_VERBOSE) {
        printf( "n = %d;\n"
                "N = \"%s\"\n",
                n, N);
    }

    char *p, *res = NULL;
    unsigned long long res_prod = 0;
    for (p = strtok(N, "0"); p; p = strtok(NULL, "0")) {
        if (strlen(p) < n) continue;
        char *q = p;
        unsigned long long prod = 1LL;
                int i;
        for (i = 0; i < n; i++) { /* initial product */
            prod *= *p++ - '0';
        }
        for(;;) {
            int larger = prod > res_prod;
            if (flags & FLAG_VERBOSE)
                printf("Trying %.*s ==> %llu%s\n",
                        n, q, prod,
                        larger ? " !" : "");
            if (larger) {
                res = q; res_prod = prod;
            }
            if (!*p) break;
            prod /= *q++ - '0';
            prod *= *p++ - '0';
        }
    }
    if (res) {
        int pos = res - N;
        printf("Largest product at position %d (%s%.*s%s): %llu\n",
               pos,
               pos ? "..." : "", n, res,
               pos < sizeof N - 1 - n ? "..." : "",
               res_prod);
    } else {
        printf("No solution found\n");
    }
}

et pour l'exécuter, il suffit d'exécuter 8 sur la ligne de commande.

Si vous ne voulez pas voir la solution, ne continuez pas à lire.


8.c

cc -o 8 8.c


0 commentaires