Ecco un programma che fattorizza una permutazione nel prodotto di cicli disgiunti
(l'avevo messo nella senzione sbagliata mi ero confuso xD)
richiami teorici :
per semplicità si può pensare ad una permutazione come ad un modo di disporre n oggetti senza ripeterli....
in realtà le permutazioni degli elementi di un insieme sono l'insieme di tutte le funzioni bigettive tra un insieme e se stesso.
se abc , acb, cab, cba, bca, bac sono permutazioni, si possono pensare come funzioni di questo tipo
che non c'entra con la prima riga!
altro esempio....
quindi f = (146)(235)
questo è il lavoro che deve fare il programma.
ecco la mia soluzione
(l'avevo messo nella senzione sbagliata mi ero confuso xD)
richiami teorici :
per semplicità si può pensare ad una permutazione come ad un modo di disporre n oggetti senza ripeterli....
in realtà le permutazioni degli elementi di un insieme sono l'insieme di tutte le funzioni bigettive tra un insieme e se stesso.
se abc , acb, cab, cba, bca, bac sono permutazioni, si possono pensare come funzioni di questo tipo
Codice:
/ a b c \
| | = f questa è la permutazione identica
\ a b c /
Codice:
/ a b c\
| | =g se seguite le immagini degli elementi vedrete un ciclo :
\ b c a/ a - > b -> c -> a e così via, la permutazione si può scrivere (abc)
altro esempio....
Codice:
/ 1 2 3 4 5 6 \
| | = f stesso ragionamento, 1 -> 4 -> 6 -> 1 e mi fermo
\ 4 3 5 6 2 1 / 2 -> 3 -> 5 -> 2 mi fermo ancora
questo è il lavoro che deve fare il programma.
ecco la mia soluzione
Codice:
#include <stdio.h>
#include<stdlib.h>
#define ORDINE printf("\n\n")
int leggiN(void);
void leggiPerm(int *, int);
void inizVettVal(int *, int, int);
void fattInCicli(int *, int);
void outputRisultati(int *, int);
int main(void)
{ int n;
n = leggiN();
int perm[n];
leggiPerm(perm, n);
ORDINE;
outputRisultati(perm, n);
printf("\npremere un tasto per continuare...");
while(getchar() != '\n');
return 0;
}
int leggiN()
{ int n;
printf("inserisci n:\n");
do { scanf("%d",&n);
if(n<2)
{
ORDINE;
printf("ERRORE: n deve essere maggiore o uguale a 2.");
ORDINE;
}
}while(n<2);
return n;
}
void leggiPerm(int *p, int n)
{ int i,j,flag;
for(i=0; i<n; i++)
do{
flag = 0;
printf("%d va in ?:\n", i+1);
scanf("%d",&p[i]);
for(j=0;j<i && p[i]!=p[j];j++);
if((p[i] < 1 || p[i] > n ) || j<i)
{
flag = 1;
ORDINE;
if(j<i)
printf("ERRORE: valore già inserito, il %d va in %d.", j+1, p[i]);
else
printf("ERRORE: inserisci valori compresi tra 1 e %d.", n);
ORDINE;
}
}while(flag);
}
void fattInCicli(int *p, int n)
{ int i, j, check[n], primo;
for(i=0; i<n; i++) // uso quest'array per stabilire se ho controllato
check[i]=1; // un elemento o meno.
// 1 significa che li devo controllare, 0 già fatto.
for(i=0; i<n; i++)
if(check[i])
{
check[i] = 0; // checked ;)
if(p[i] != i+1) // se l'elemento non è tenuto fisso dalla permutazione...
{
j = i;
primo = j+1;
printf("(%d",j+1);
while(p[j] != j+1 && p[j] != primo)
{
printf("%d", p[j]);
j = p[j] -1;
check[j] = 0;
}
printf(")");
}
}
}
void outputRisultati(int *p, int n)
{ int i;
printf(" / ");
for(i=0; i<n; i++)
printf("%d ",i+1);
printf("\\\n");
printf("f =|");
for(i=0; i<n; i++)
printf(" ");
printf(" | = ");
fattInCicli(p, n);
printf("\n");
printf(" \\ ");
for(i=0; i<n; i++)
printf("%d ",p[i]);
printf("/\n");
}