View Full Version : Help con creazione di lista in C
<B>Pietro<B>
06-02-2013, 17:27
Ciao a tutti… perché in questo codice risulta l'ultimo valore molto più elevato del limite imposto?
(Do per scontato le dichiarazioni delle variabili e degli #include)
#include <stdio.h>
#define DIM 100
int i;
int a[DIM];
//Es 1: Creo e stampo la lista
for(i=0;i!=DIM-1;i++){
a[i]=rand()%1000;
printf("%d ",a[i]);
}
printf("\n");
Inoltre, non riesco a togliere le ripetizioni di numeri… dopo pubblico il codice intero, un problema alla volta :-)
Grazie per l'aiuto :-)
Miky Mouse
06-02-2013, 21:57
risulta l'ultimo valore molto più elevato del limite imposto?
che vuol dire questa frase?
a me sembra che vada tutto bene... forse ti stai chiedendo perché si ferma a 99 elementi? perché quando arrivi a 100 non entri proprio nel ciclo... una possibile soluzione è usare
for(i=0;i<DIM;i++)
se invece hai problemi con "il valore" assunto dall'ultimo elemento del vettore a, quello dipende dalla funzione rand (che è random...)
però non capisco "il limite" quale sia...
<B>Pietro<B>
06-02-2013, 22:05
hai ragione la mia spiegazione è stata pessima… :D
Quando io creo la lista con valori casuali (in questo caso di limite random 1000), viene creato un valore della lista con valori in milioni se non in miliardi. Mi chiedo: che cosa ho fatto di così terribile perché si crei una cosa del genere? D:
Grazie :)
Ma è quel ciclo for che ti stampa a schermo un valore anomalo? e qual'è l'indice del valore anomalo? Se leggi ad aree di memoria non inizializzate puoi ottenere qualsiasi numero.
Hai modificato la condizione di uscita come ti ha detto l'utente sopra?
Miky Mouse
07-02-2013, 08:25
puoi postare il codice che realmente utilizzi senza dare per scontato niente?
hai ragione la mia spiegazione è stata pessima… :D
Quando io creo la lista con valori casuali (in questo caso di limite random 1000), viene creato un valore della lista con valori in milioni se non in miliardi. Mi chiedo: che cosa ho fatto di così terribile perché si crei una cosa del genere? D:
Grazie :)
io con questo codice (fatto copia/incolla dal mio):
#include <stdio.h>
#define DIM 100
int main(){
int i,a[DIM];
for(i=0;i<DIM;i++){
a[i]=rand()%1000;
printf("%d (%d)\n",a[i],i);
}
}
ottengo questo output (tra 0 e 999 come dovrebbe)...
807 (0)
249 (1)
73 (2)
658 (3)
930 (4)
272 (5)
544 (6)
878 (7)
923 (8)
709 (9)
440 (10)
165 (11)
492 (12)
42 (13)
987 (14)
503 (15)
327 (16)
729 (17)
840 (18)
612 (19)
303 (20)
169 (21)
709 (22)
157 (23)
560 (24)
933 (25)
99 (26)
278 (27)
816 (28)
335 (29)
97 (30)
826 (31)
512 (32)
267 (33)
810 (34)
633 (35)
979 (36)
149 (37)
579 (38)
821 (39)
967 (40)
672 (41)
393 (42)
336 (43)
485 (44)
745 (45)
228 (46)
91 (47)
194 (48)
357 (49)
1 (50)
153 (51)
708 (52)
944 (53)
668 (54)
490 (55)
124 (56)
196 (57)
530 (58)
903 (59)
722 (60)
666 (61)
549 (62)
24 (63)
801 (64)
853 (65)
977 (66)
408 (67)
228 (68)
933 (69)
298 (70)
981 (71)
635 (72)
13 (73)
865 (74)
814 (75)
63 (76)
536 (77)
425 (78)
669 (79)
115 (80)
94 (81)
629 (82)
501 (83)
517 (84)
195 (85)
105 (86)
404 (87)
451 (88)
298 (89)
188 (90)
123 (91)
505 (92)
882 (93)
752 (94)
566 (95)
716 (96)
337 (97)
438 (98)
144 (99)
<B>Pietro<B>
08-02-2013, 18:07
Avete ragione… mi sono sbagliato perché è dopo che cambia la lista, ma non so perché…
/*
* Esercizio 1 LISTA:
* 1. Visualizzare il vettore di una lista con elementi generati casualmente
* 2. Cercare e trovare il valore minimo
* 3. Cercare e trovare il valore massimo
* 4. Ordinare il vettore in modo crescente
* 5. Eliminare gli elementi ripetitivi e compattare a sinistra (non lasciare gli spazi vuoti)
*
* Created by Pietro on 15/12/2012.
* Copyright 2012. All rights reserved.
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define DIM 100
/*
int Scorri_e_inserisci(int a[]){
int i;
for (i=0; i<=100;i++) {
if(a[i]>=0){
return a;
}
}
}
*/
//Variabili
int main(){
srand(time(NULL));
int a[DIM];
int i,j,l,tmp;
int min,max;
int guardia=1;
int somma=0;
//int b[DIM];
//Es 1: Creo e stampo la lista
for(i=0;i!=(DIM-1);i++){
a[i]=rand()%1000;
printf("%d ",a[i]);
}
printf("\n");
//Es 2
min=a[0];
for(i=0;i<=DIM;i++){
if(a[i]<min){
min=a[i];
}
}
printf("\nIl valore minimo e' %d\n",min);
//Es 3
max=a[0];
for(i=0;i<=DIM;i++){
if(a[i]>max){
max=a[i];
}
}
printf("Il valore massimo e' %d\n",max);
//Es 4
for(j=0;j<=DIM;j++){
for(i=0;i<=100;i++){
if(a[j]<a[i]){
tmp=a[j];
a[j]=a[i];
a[i]=tmp;
}
}
}
//Stampa la lista
for(i=0;i<=DIM;i++){
printf("%d ",a[i]);
}
printf("\n\n");
getchar();
return 0;
}
<B>Pietro<B>
08-02-2013, 18:24
Ragazzi non riesco a togliere le ripetizioni… qualche aiuto?
/*
* Esercizio 1 LISTA:
* 1. Visualizzare il vettore di una lista con elementi generati casualmente
* 2. Cercare e trovare il valore minimo
* 3. Cercare e trovare il valore massimo
* 4. Ordinare il vettore in modo crescente
* 5. Eliminare gli elementi ripetitivi e compattare a sinistra (non lasciare gli spazi vuoti)
*
* Created by Pietro Cesaraccio on 15/12/2012.
* Copyright 2012. All rights reserved.
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define DIM 100
/*
int Scorri_e_inserisci(int a[]){
int i;
for (i=0; i<=100;i++) {
if(a[i]>=0){
return a;
}
}
}
*/
//Variabili
int main(){
srand(time(NULL));
int a[DIM];
int i,j,l,tmp;
int min,max;
int somma=0;
//int b[DIM];
//Es 1: Creo e stampo la lista
for(i=0;i!=(DIM-1);i++){
a[i]=rand()%1000;
printf("%d ",a[i]);
}
printf("\n");
//Es 2
min=a[0];
for(i=0;i<DIM;i++){
if(a[i]<min){
min=a[i];
}
}
printf("\nIl valore minimo e' %d\n",min);
//Es 3
max=a[0];
for(i=0;i<DIM;i++){
if(a[i]>max){
max=a[i];
}
}
printf("Il valore massimo e' %d\n",max);
//Es 4
for(j=0;j<DIM;j++){
for(i=0;i<DIM;i++){
if(a[j]<a[i]){
tmp=a[j];
a[j]=a[i];
a[i]=tmp;
}
}
}
//Es 5
for(i=0;i<DIM;i++){
for(j=i+1;i<DIM;i++){
if(i==j){ //Se l'elemento i e' ripetuto nei valori successivi j
for (l=j; l<DIM-1; l++) {
//printf("\n%d %d %d",a[i],a[j],tmp);
a[l]=a[l+1];
}
}
}
}
//Stampa la lista compattata senza ripetizioni
for(i=0;i<DIM;i++){
printf("%d ",a[i]);
}
//Media aritmetica
for (i=0; i<DIM; i++) {
somma+=a[i];
}
printf("\nLa media aritmetica dei valori della lista e' %d",somma/(DIM-1));
getchar();
return 0;
}
Per stamparli ordinati e automaticamente escludere i doppi, prova così:
for(i=0;i<DIM;i++)
{
while (last == a[i] && i < DIM)
i++;
printf("%d ",a[i]);
last = a[i];
}
Devi dichiarare una variabile intera di nome last e impostarla a -1:
int main(void){
//Variabili varie
int last=-1;
//Codice vario
for(i=0;i<DIM;i++)
{
while (last == a[i] && i < DIM)
i++;
printf("%d ",a[i]);
last = a[i];
}
In pratica, un approccio semplice: siccome i numeri generati non sono mai minori di 0, imposto last a -1 ( per essere sicuro che non prenda valori che possano entrare in conflitto con quelli che sto analizzando ).
Fatto ciò controllo se last è uguale a a[i], al primo giro non lo è mai.
Se non è uguale, non entro nel while.
Stampo il numero.
Salvo il numero stampato in last.
Continuo fino alla fine.
Se non hai capito, fa sapere.
non ho provato a farlo girare perchè ora non posso, però leggendo la parte dell'esercizio 5 (non ho guardato il resto, nel post chiedi su come eliminare i doppioni)
//Es 5
for(i=0;i<DIM;i++){
for(j=i+1;i<DIM;i++){
if(i==j){ //Se l'elemento i e' ripetuto nei valori successivi j
for (l=j; l<DIM-1; l++) {
//printf("\n%d %d %d",a[i],a[j],tmp);
a[l]=a[l+1];
}
}
}
}
in pratica faresti un ciclo per scorrere l'array (il termine "lista" mi aveva ingannato e non capivo all'inizio :asd:) su i nel primo for, e per ogni i-esimo elemento scorri il resto dell'array per cercare i doppioni con il secondo for su j; poi se lo trovi sposti tutto di uno indietro.
Il fatto è che usando un array, questo avrà sempre la stessa lunghezza, quindi se copi indietro dei valori perchè trovi dei duplicati, ne avrai sempre in fondo, es:
[1|2|3|3|4|5] ==diventa==> [1|2|3|4|5|5] perchè il 5 va dove c'era il 4 ma al posto di dove c'era il primo 5 non ci va niente perchè sei arrivato in fondo all'array.
Quindi concettualmente potresti tenere traccia tramite un contatore di quanti duplicati trovi e poi accorciare l'array con una realloc().
Un'altra cosa che non mi torna è che nel secondo ciclo for(j=i+1;i<DIM;i++):
credo che dovresti usare j così: for(j=i+1;j<DIM;j++) perchè altrimenti incrementeresti sempre i.
Poi if(i==j){ //Se l'elemento i e' ripetuto nei valori successivi j:
qui confronti gli indici che usi per scorrere l'array, mentre per confrontare i valori e vedere se sono doppi dovresti fare if(a[i]==a[j]) (l'elemento i-esimo è array[i], non i).
forse c'è altro ma ora come ora non posso testarlo direttamente :asd:
EDIT: probabilmente ho detto un mare di vaccate, e mentre le stavo scrivendo, il mio quasi concittadino aveva già risposto sicuramente meglio di me :asd:
EDIT2: "//Variabili varie" mi piace :asd:
:asd:
All'inizio avevo pensato di spostare gli indirizzi in memoria, poi ho detto "potremmo riallocare il vettore"... ;)
Poi ho pensato, mmm mi sa che è troppo per chi è agli inizi con C.
Ho cercato la soluzione più semplice. Spero sia di facile comprensione.
EDIT: La prima soluzione non si può attuare con i vettori.
<B>Pietro<B>
08-02-2013, 21:58
Ora funziona:
/*
* Esercizio 1 LISTA:
* 1. Visualizzare il vettore di una lista con elementi generati casualmente
* 2. Cercare e trovare il valore minimo
* 3. Cercare e trovare il valore massimo
* 4. Ordinare il vettore in modo crescente
* 5. Eliminare gli elementi ripetitivi e compattare a sinistra (non lasciare gli spazi vuoti)
*
* Created by Pietro Cesaraccio on 15/12/2012.
* Copyright 2012. All rights reserved.
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define DIM 100
//Variabili
int main(){
srand(time(NULL));
int a[DIM];
int i,j,tmp;
int min,max;
int last=-1;
int somma=0;
//Es 1: Creo e stampo la lista
printf("Creo una lista casuale di interi: \n");
for(i=0;i!=(DIM-1);i++){
a[i]=rand()%1000;
printf("%d ",a[i]);
}
printf("\n");
//Es 2
min=a[0];
for(i=0;i<DIM;i++){
if(a[i]<min){
min=a[i];
}
}
printf("\nIl valore minimo e' %d\n",min);
//Es 3
max=a[0];
for(i=0;i<DIM;i++){
if(a[i]>max){
max=a[i];
}
}
printf("Il valore massimo e' %d\n\n",max);
//Es 4
for(j=0;j<DIM;j++){
for(i=0;i<DIM;i++){
if(a[j]<a[i]){
tmp=a[j];
a[j]=a[i];
a[i]=tmp;
}
}
}
//Es 5 e stampa
for(i=0;i<DIM;i++){
while (last == a[i] && i < DIM){
i++;
}
printf("%d ",a[i]);
last = a[i];
}
printf("\n");
//Media aritmetica
for (i=0; i<DIM; i++) {
somma+=a[i];
}
printf("\nLa media aritmetica dei valori della lista e' %d",somma/(DIM-1));
getchar();
return 0;
}
Quindi concettualmente potresti tenere traccia tramite un contatore di quanti duplicati trovi e poi accorciare l'array con una realloc().
Un'altra cosa che non mi torna è che nel secondo ciclo for(j=i+1;i<DIM;i++):
credo che dovresti usare j così: for(j=i+1;j<DIM;j++) perchè altrimenti incrementeresti sempre i.
Poi if(i==j){ //Se l'elemento i e' ripetuto nei valori successivi j:
qui confronti gli indici che usi per scorrere l'array, mentre per confrontare i valori e vedere se sono doppi dovresti fare if(a[i]==a[j]) (l'elemento i-esimo è array[i], non i).
Ho provato a sistemare i for come hai detto (senza il realloc() che non so cosa sia :asd:), però mi dà errore all'if(a[i]==a[j])… boh.
In ogni caso grazie mille ragazzi, ora funziona tutto alla perfezione :-).
Giusto per curiosità: per andare a capo esiste qualcosa di veloce o bisogna ogni volta inserire un printf("\n"); ?
Giusto per curiosità: per andare a capo esiste qualcosa di veloce o bisogna ogni volta inserire un printf("\n"); ?
printf("%c",10);
:asd:
a parte gli scherzi, no
Giusto per curiosità: per andare a capo esiste qualcosa di veloce o bisogna ogni volta inserire un printf("\n"); ?
È C, non python o chissà quale altro linguaggio di alto livello :D
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.