Re: QUADRATO MAGICO

di il
29 risposte

29 Risposte - Pagina 2

  • Re: Re: QUADRATO MAGICO

    Non hai capito ... io non voglio farti perdere tempo. Il mio è un consiglio.
  • Re: Re: QUADRATO MAGICO

    Weierstrass ha scritto:


    Posta il codice originale oppure posta la matrice fatta a manina
    Non siamo telepati
    Subito ti faccio vedere quello che ho scritto io:
    int generazione_num_cas(int [][dim]);
    int confronto_numeri(int , int [][dim]);
    int main()
    {
        int a[10][10];
        int i,j;
    
        //Stampa quadrato
        for (i=0;i<dim;i++)
        {
            printf("\n");
            for (j=0;j<dim;j++)
            {
                printf("|%d|",generazione_num_cas(a[i][j]));
    
            }
        }
    }
    int generazione_num_cas(int a[][dim])
    {
        srand(time(NULL));
    
        int i, j,num;
    
        for (i=0;i<dim;i++){
            for (int j=0 ;j<dim; j++)
            {
                //num=rand()%(dim*dim)+1;
                while(confronto_numeri(num,a)==1)
                    num = rand() % (dim*dim) + 1;
                a[i][j] = num;
            }
        }
    }
    int confronto_numeri(int num,int a[][dim]){
        int i,j;
        for(i=0; i<dim; i++){
            for(j=0; j<dim; j++)
                if(num == a[i][j])
                    return 1;
        }
        return 0;
    
    }
  • Re: Re: QUADRATO MAGICO

    Weierstrass ha scritto:


    Posta il codice originale oppure posta la matrice fatta a manina
    Non siamo telepati
    Mentre il codeice originale è questo:
    #include <stdlib.h>
    #include <time.h>
    #include <stdio.h>
    #define DIM 3
    void generazione(int mat[][DIM]);
    void inizializza(int mat[][DIM]);
    void stampa(int mat[][DIM]);
    int confronto(int num,int mat[][DIM]);
    int magica(int mat[][DIM]);
    int main(){
    	srand(time(NULL));
    	int mat[DIM][DIM],i,flag=0,x,somma=0;
    	long int cont=0;
    	//int mat2[DIM][DIM]={ {2,7,6},{9,5,1},{4,3,8} };
    	cont=0;
    	flag=0;
    	while(flag==0){
    		generazione(mat);
    		if(magica(mat)){
    			stampa(mat);
    			printf("\n");
    			printf("cont = %d\n", cont);
    			flag=1;
    		}
    		cont++;
    	}
    }
    
    void generazione(int mat[][DIM]){
    	int num,i,j;
    	inizializza(mat);
    	for(i=0; i<DIM; i++)
    		for(j=0; j<DIM; j++){
    			num = rand() % (DIM*DIM) + 1;
    			while(confronto(num,mat)==1)
    					num = rand() % (DIM*DIM) + 1;
    			mat[i][j] = num;
    		}
    }
    
    
    void inizializza(int mat[][DIM]){
    	int i,j;
    	for(i=0; i<DIM; i++)
    		for(j=0; j<DIM; j++)
    			mat[i][j]=0;
    }
    
    void stampa(int mat[][DIM]){
    	int i,j;
    	for(i=0; i<DIM; i++){
    		for(j=0; j<DIM; j++)
    			printf("%d ",mat[i][j]);
    		printf("\n");
    	}
    }
    
    int confronto(int num,int mat[][DIM]){
    	int i,j;
    	for(i=0; i<DIM; i++){
    		for(j=0; j<DIM; j++)
    			if(num == mat[i][j])
    				return 1;
    	}
    	return 0;
    
    }
    
    int magica(int mat[][DIM]){
    	int somma1=0, somma2=0,i,j;
    	for(i=0; i<DIM; i++)
    		somma1 = somma1 + mat[i][i]; // valori sulla(sopra) diagonale
    
    	for(i=0; i<DIM; i++){			//confronto righe con somma
    		for(j=0,somma2=0; j<DIM; j++)
    			somma2=somma2+mat[i][j];
    		if(somma2!=somma1)
    			return 0;
    	}
    
    	for(i=0; i<DIM; i++){			//confronto colonne con somma
    		for(j=0,somma2=0; j<DIM; j++)
    			somma2=somma2+mat[j][i];
    		if(somma2!=somma1)
    			return 0;
    	}
    	for(i=0,somma2=0,j=DIM-1; i<DIM; i++,j--)
    		somma2=somma2+mat[i][j];                //DIAGONALI INSIEME
    	if(somma2!=somma1)
    		return 0;
    	return 1;
    	}
    
  • Re: Re: QUADRATO MAGICO

    Comincia con spiegare perché hai cambiato la funzione

    void generazione(int mat[][DIM]);

    in

    int generazione(int mat[][DIM]);

    e come mai questa veniva chiamata con

    generazione(mat);

    mentre tu la chiami con

    printf("|%d|",generazione_num_cas(a[ i ][ j ]));
  • Re: Re: QUADRATO MAGICO

    Per quanto riguarda la chiamata penso si possa fare in due modi mentre per il fatto del void non pensavo servisse una funzione di quel tipo ma andassse bene la funzione con int.
  • Re: Re: QUADRATO MAGICO

    Pensi male. C'è differenza ma perché l'hai modificata non lo spieghi. Non va modificata infatti
  • Re: Re: QUADRATO MAGICO

    oregon ha scritto:


    Pensi male. C'è differenza ma perché l'hai modificata non lo spieghi. Non va modificata infatti
    Sono ripartito da zero a modo mio ora sono fermo a questo punto ora devo eseguire le operazioni per capire se e magico o meno. Potresti darmi una mano?
    
    void riempi_arr(int a[][n]);              //riempirlo di 0 per leggere tutta la matrice
    int in_arr(int a[][n],int num);          //per verificare se il numero inserito sia gia presente nella matrice
    int operazioni(int a[][n]);
    
    
    int main()
    {
        srand(time(NULL));
        int a[n][n];
        riempi_arr(a);                                                  //riempimento della matrice
        int i,j;
        int num;
    
        //Generazione e stampa del quadrato
        for (i = 0; i < n; i++)
        {   printf("\n");                                      //per far si che si visualizzi un quadrato
            for (j = 0; j < n; j++)
            {
                while (in_arr(a, num= 1 + rand() % (n*n)));     //condizione per non far ripetere i numeri
                a[i][j]= num;
                printf("|%d|", a[i][j]);
    
            }
        }
        return 0;
    }
    int in_arr(int a[][n],int num)
    {
        for ( int i = 0; i < n; i++) {
            for ( int j = 0; j < n; j++){
                if(num == a[i][j]){
                    return 1;
                }
            }
        }
        return 0;
    }
    void riempi_arr(int a[][n])
    {
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                a[i][j]=0;
            }
        }
    }
    int operazioni(int a[][n])
    {
        int somma1=0, somma2=0;
        int i,j;
        for(i=0; i<n; i++)
            somma1 = somma1 + a[i][i];      // valori sulla(sopra) diagonale
    
        for(i=0; i<n; i++){			        //confronto righe con somma
            for(j=0,somma2=0; j<n; j++)
                somma2=somma2+a[i][j];
            if(somma2!=somma1)
                return 0;
        }
    
        for(i=0; i<n; i++){			        //confronto colonne con somma
            for(j=0,somma2=0; j<n; j++)
                somma2=somma2+a[j][i];
            if(somma2!=somma1)
                return 0;
        }
        for(i=0,somma2=0,j=n-1; i<n; i++,j--)
            somma2=somma2+a[i][j];                //DIAGONALI INSIEME
        if(somma2!=somma1)
            return 0;
        return 1;
    }
    
  • Re: Re: QUADRATO MAGICO

    Ammine7 ha scritto:


    mi sono servito di vecchi post sul forum
    Mi sembra però che tu non lo abbia letto attentamente quel vecchio topic...

    Per esempio conosci la relazione che sussiste tra "costante magica" e ordine di un quadrato magico perfetto?
  • Re: Re: QUADRATO MAGICO

    Nippolo ha scritto:


    Ammine7 ha scritto:


    mi sono servito di vecchi post sul forum
    Mi sembra però che tu non lo abbia letto attentamente quel vecchio topic...

    Per esempio conosci la relazione che sussiste tra "costante magica" e ordine di un quadrato magico perfetto?
    Si ho capito la differenza tramite la tua spiegazione si calcola tramite la formula M = [n(n^2+1)]/2 se non sbaglio, adesso sto usando un'approccio piu sempice ovvero calcolarmi una costante magica per poi richiamarmela in ogni confronto tra righe/colonne/diagonali. che dici puo funzionare impostato cosi oppure ho preso una strada sbagliata?
  • Re: Re: QUADRATO MAGICO

    Calcolata la costante magica M, appena trovi una sequenza (riga, colonna o diagonale) la cui somma è diversa da M puoi già concludere che il quadrato non è magico.
  • Re: Re: QUADRATO MAGICO

    Nippolo ha scritto:


    Calcolata la costante magica M, appena trovi una sequenza (riga, colonna o diagonale) la cui somma è diversa da M puoi già concludere che il quadrato non è magico.
    Ho completato il codice sono indeciso sul calcolo della diagonale secondaria (quella che parte da in alto a destra) e poi devo implementare la probabilita che in 1000 tentativi devo vedere quanti quadrati mi escono il codice è questo se puoi aiutarmi a capire saresti gentilissimo.
    #include <stdio.h>
    #include <stdlib.h>
    #include <time.h>
    #define n 3                                //Definisce la grandezza del quadrato (es. 3x3/4x4...)
    
    
    void riempi_arr(int a[][n]);              //riempirlo di 0 per leggere tutta la matrice
    int in_arr(int a[][n],int num);          //per verificare se il numero inserito sia gia presente nella matrice
    int operazioni(int a[][n],int );
    int costante_magica();
    
    
    int main()
    {
        srand(time(NULL));
        int a[n][n];
        riempi_arr(a);                                                  //riempimento della matrice
        int i,j;
        int num,co_mg;
    
        //Generazione e stampa del quadrato
        for (i = 0; i < n; i++) {
            printf("\n");                                      //per far si che si visualizzi un quadrat
            for (j = 0; j < n; j++) {
                while (in_arr(a, num = 1 + rand() % (n * n)));     //condizione per non far ripetere i numeri
                a[i][j] = num;
                printf("|%d|", a[i][j]);
            }
        }
            co_mg=costante_magica(a);
            printf("\n%d",operazioni(a,co_mg));
            return 0;
    }
    int in_arr(int a[][n],int num)
    {
        for ( int i = 0; i < n; i++) {
            for ( int j = 0; j < n; j++){
                if(num == a[i][j]){
                    return 1;
                }
            }
        }
        return 0;
    }
    void riempi_arr(int a[][n])
    {
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                a[i][j]=0;
            }
        }
    }
    int costante_magica()
    {
        return (n *(n * n + 1)) /2;
    }
    int operazioni(int a[][n], int cm)
    {
        int somma_1=0, somma_2=0;
        int i,j;
    
        // Calcolo valori sopra alle diagonali
        for(i=0; i<n; i++)
            somma_1 = somma_1 + a[i][i];
        if(somma_1!=costante_magica())
            return 0;
    
        //Calcolo delle righe e confronto
        for(i=0; i<n; i++){
            for(j=0,somma_2=0; j<n; j++)
                somma_2=somma_2+a[i][j];
            if(somma_2!=costante_magica())
                return 0;
        }
        //Calcolo delle colonne e confronto
        for(i=0; i<n; i++){
            for(j=0,somma_2=0; j<n; j++)
                somma_2=somma_2+a[j][i];
            if(somma_2!=costante_magica())
                return 0;
        }
        //Calcolo somma delle diagonali
        for(i=0,somma_2=0,j=n-1; i<n; i++,j--)
            somma_2=somma_2+a[i][j];
        if(somma_2!=costante_magica())
           return 0;
    
        return 1;
    }
  • Re: Re: QUADRATO MAGICO

    - la funzione riempi_arr() è inutile, per inizializzare l'intera matrice a 0 basta scrivere
    int a[N][N] = {0};
    - non vale la pena utilizzare una funzione per eseguire una singola istruzione, quindi via anche costante_magica();
    - relativamente alla generazione del quadrato casuale qui trovi la mia idea al riguardo:
    https://www.iprogrammatori.it/forum-programmazione/post8619551.html#p8619551
    https://www.iprogrammatori.it/forum-programmazione/post8619570.html#p8619570
    - se ti interessa, nell'ultimo post linkato trovi anche "un'analisi probabilistica" del problema (da cui ti renderai conto che su 1000 quadrati casuali, a meno di essere mooooooolto fortunato, non troverai nessun quadrato magico);
    - per quanto riguarda la funzione operazioni() appena ho tempo gli darò un'occhiata.
  • Re: Re: QUADRATO MAGICO

    Nippolo ha scritto:


    - la funzione riempi_arr() è inutile, per inizializzare l'intera matrice a 0 basta scrivere
    int a[N][N] = {0};
    - non vale la pena utilizzare una funzione per eseguire una singola istruzione, quindi via anche costante_magica();
    - relativamente alla generazione del quadrato casuale qui trovi la mia idea al riguardo:
    https://www.iprogrammatori.it/forum-programmazione/post8619551.html#p8619551
    https://www.iprogrammatori.it/forum-programmazione/post8619570.html#p8619570
    - se ti interessa, nell'ultimo post linkato trovi anche "un'analisi probabilistica" del problema (da cui ti renderai conto che su 1000 quadrati casuali, a meno di essere mooooooolto fortunato, non troverai nessun quadrato magico);
    - per quanto riguarda la funzione operazioni() appena ho tempo gli darò un'occhiata.
    Non sono menefreghista ma per il momento non ho apportato quelle modifiche che mi hai detto prima comunque ho provato con tutti i quadrati (2x2, 3x3,4x4) ma non mi trova nemmeno un quadrato con pure 5000 tentativi anche con 10000 ho provato eppure il codice è giusto vi prego date un occhiata sto perdendo la testa
    #include <stdio.h>
    #include <stdlib.h>
    #include <time.h>
    #define n 3                                //Definisce la grandezza del quadrato (es. 3x3/4x4...)
    
    void riempi_arr(int a[][n]);              //riempirlo di 0 per leggere tutta la matrice
    int in_arr(int a[][n],int num);          //per verificare se il numero inserito sia gia presente nella matrice
    int operazioni(int a[][n],int );
    int costante_magica();
    
    int main()
    {
            int contatore;
            int num_esec=0;
            for (contatore = 0;contatore <5000;contatore++)
            {
                srand(time(NULL));
                int a[n][n];
                riempi_arr(a);                 //riempimento della matrice
                int i, j;
                int num;
    
                //Generazione e stampa del quadrato
                for (i = 0; i < n; i++) {
                    printf("\n");               //per far si che si visualizzi la forma di un quadrato
                    for (j = 0; j < n; j++) {
                        while (in_arr(a, num = 1 + rand() % (n * n)));     //per non far si che i numeri non si ripetano
                        a[i][j] = num;
                        printf("|%d|", a[i][j]);
                    }
                }
                int co_mg = costante_magica(a);
                printf("\n Quadrato numero:%d",contatore);
                printf("\n%d", operazioni(a, co_mg));
    
            }
            printf("\n La percentuale di trovare un quadrato magico e':%f",(num_esec/1000)*100);
    
    return 0;
    }
    int in_arr(int a[][n],int num)
    {
        for ( int i = 0; i < n; i++) {
            for ( int j = 0; j < n; j++){
                if(num == a[i][j]){
                    return 1;
                }
            }
        }
        return 0;
    }
    void riempi_arr(int a[][n])
    {
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                a[i][j]=0;
            }
        }
    }
    int costante_magica()
    {
        return (n *(n * n + 1)) /2;
    }
    int operazioni(int a[][n], int cm)
    {
        int somma_1=0, somma_2=0;
        int i,j;
    
        // Calcolo valori sopra alle diagonali
        for(i=0; i<n; i++)
            somma_1 = somma_1 + a[i][i];
        if(somma_1!=costante_magica())
            return 0;
    
        //Calcolo delle righe e confronto
        for(i=0; i<n; i++){
            for(j=0,somma_2=0; j<n; j++)
                somma_2=somma_2+a[i][j];
            if(somma_2!=costante_magica())
                return 0;
        }
        //Calcolo delle colonne e confronto
        for(i=0; i<n; i++){
            for(j=0,somma_2=0; j<n; j++)
                somma_2=somma_2+a[j][i];
            if(somma_2!=costante_magica())
                return 0;
        }
        //Calcolo somma delle diagonali
        for(i=0,somma_2=0,j=n-1; i<n; i++,j--)
            somma_2=somma_2+a[i][j];
        if(somma_2!=costante_magica())
           return 0;
    
        return 1;
    }
  • Re: Re: QUADRATO MAGICO

    Menefreghista non so, ma un po' svogliato di sicuro... infatti se avessi letto il post che ti ho linkato avresti saputo che la probabilità di generare un quadrato magico è circa 1/45000.

    In ogni caso il seme per generare i numeri casuali va inizializzato una sola volta e al fine di rendere l'esecuzione del programma più veloce ti consiglio di limitarti a stampare solo gli eventuali quadrati magici trovati.

    P.S.
    La funzione operazioni() potrebbe essere migliorata, ma nel complesso mi sembra comunque corretta.
  • Re: Re: QUADRATO MAGICO

    Nippolo ha scritto:


    Menefreghista non so, ma un po' svogliato di sicuro... infatti se avessi letto il post che ti ho linkato avresti saputo che la probabilità di generare un quadrato magico è circa 1/45000.

    In ogni caso il seme per generare i numeri casuali va inizializzato una sola volta e al fine di rendere l'esecuzione del programma più veloce ti consiglio di limitarti a stampare solo gli eventuali quadrati magici trovati.

    P.S.
    La funzione operazioni() potrebbe essere migliorata, ma nel complesso mi sembra comunque corretta.
    Ciao, ti assicuro che ho letto il tuo post piu volte e dopo aver migliorato il programma mi trovo con te, ora ho implementato alcune cose ma il programma va in loop poi penso sia finito.
    Ho un problema nel ciclo while secono me poiche al massimo l'utente puo inserire 3 volte la dimensione del quadrato ma continua all'infinito, non mi dite fallo con i puntatori ecc... perche non sono stato in grado, se potete magari dirmi dove ho sbagliato vi sarei grato, grazie in anticipo.
    #include "header.h"
    int main()
    {
    #include <stdio.h>
    #include <stdlib.h>
    #include <time.h>
    #define MAX 100                              //Definisce la massima grandezza del quadrato (es. 3x3/4x4...)
    
    void riempi_arr(int a[][MAX], int);              //Riempirlo di 0 per leggere tutta la matrice
    int in_arr(int a[][MAX],int num, int );          //per verificare se il numero inserito sia gia presente nella matrice
    int operazioni(int a[][MAX],int ,int );
    int costante_magica(int );
    
    
        int contatore;
        int conta_volte=3;       /*Le vote in cui chiedo di inserire una nuova matrice*/
        int trovate_tot=0;
        int dim_utente=0;
        int a[MAX][MAX];
    
    
        srand(time(NULL));
        while(conta_volte <= 3)
        {
            conta_volte --;
            printf("\n Inserire la dimensione che deve avere il quadrato:");
            scanf("%d",&dim_utente);
    
            riempi_arr(a,MAX);
    
    
            for (contatore = 0;contatore <1000;contatore++)
            {
                int esecuz_op=0;
                riempi_arr(a,dim_utente);                                 //riempimento della matrice
                int i, j;
                int num;
    
                //Generazione e stampa del quadrato
                for (i = 0; i < dim_utente; i++) {
                    for (j = 0; j < dim_utente; j++) {
                        while (in_arr(a, num = 1 + rand() % (dim_utente * dim_utente),dim_utente));  //per non far ripetere i numeri
                        a[i][j] = num;
                    }
                }
                int co_mg = costante_magica(dim_utente);                              //assegnazione costante magica
    
                printf("\n Quadrato numero:%d",contatore);
                    esecuz_op=operazioni(a, co_mg,dim_utente);
    
                if(esecuz_op == 0) {
                    printf ("\n ******Trovato****** \n");
                    trovate_tot++;
                    printf("\n La percentuale parziale di trovare un quadrato magico e': %f",(trovate_tot*100/(float)contatore));
    
                    for (i = 0; i < dim_utente; i++) {
                        printf("\n");                           /*per far si che si visualizzi la forma
                                                                        *di un quadrato*/
                        for (j = 0; j < dim_utente; j++) {
                            printf("|%d|", a[i][j]);            /*scrivo la matrice trovata*/
                        }
                    }
                    printf("\n\n Premi invio per continuare a cercare");
                    getchar();                                       /*blocca il programma per leggere*/
                }
            }
            printf("\n\n I quadrati che sono stati trovati sono :%d \n ",trovate_tot);
            printf("\n La percentuale totale di trovare un quadrato magico e': %f",(trovate_tot*100/(float)contatore));
        }
            return 0;
    }
    
    Se servono anche le function:
    int in_arr(int a[][100],int num,int n_ut)
    {
        for ( int i = 0; i < n_ut; i++) {
            for ( int j = 0; j < n_ut; j++){
                if(num == a[i][j]){
                    return 1;
                }
            }
        }
        return 0;
    }
    void riempi_arr(int a[][100],int n_ut)
    {
        for (int i = 0; i < n_ut; i++) {
            for (int j = 0; j < n_ut; j++) {
                a[i][j]=0;
            }
        }
    }
    int costante_magica(int n_ut)
    {
        return (n_ut *(n_ut * n_ut + 1)) /2;
    }
    int operazioni(int a[][100], int magic,int n_ut)
    {
        int i,j;                            //(i su righe, j su colonne)
        int som_rig,som_col,som_d1,som_d2;
    
        /*controllo delle RIGHE*/
    
        som_rig=0;
        for(i=0; i < n_ut;i++) {
            for(j=0; j< n_ut; j++)
                som_rig+=a[i][j];
            if (som_rig!=magic)
                return 6;                          /*6 codice errore sulle righe*/
            else
                som_rig=0;
        }
        /*controllo delle COLONNE*/
    
        som_col=0;
        for(j=0; j < n_ut; j++){
            for(i=0; i < n_ut; i++)
                som_col+=a[i][j];
            if (som_col!=magic)
                return 7;                        /*7 codice errore sulle righe*/
            else
                som_col=0;
        }
    
        /*controllo della Prima Diagonale Principale (Dx)*/
    
        som_d1=0;
        for(i=0; i < n_ut; i++)
            som_d1+=a[i][i];
        if(som_d1!=magic)
            return 8;                   /*8 codice errore diagonale 1*/
    
        /*controllo della Seconda Diagonale Principale (Sx)*/
        som_d2=0;
        for(i=0; i < n_ut;i++)
            som_d2+=a[i][n_ut-1-i];     /*forse n-i*/
        if(som_d2!=magic)
            return 9;                /*9 codice errore su diagonale 2*/
    
        return 0;                   /*0 codice che indica che è un quadrato magico*/
        }
    
Devi accedere o registrarti per scrivere nel forum
29 risposte