Newsgroup: it.comp.lang.c
Titolo: Lista ordinata!!

Raazzi il mio problema e' questo:
devo leggere tutte le parole di un file testo e poi copiarle ordinate
alfabeticamente in un altro file.
La stessa cosa la devo ripetere ordinando le parole per lunghezza.
Avevo pensato di copiare tutte le parole in una lista e poi ordinarle
alfabeticamente, che ne pensate??
Ma come cavolo si ordina una lista dinamica alfabeticamente??
Grazie in anticipo.

 ha scritto nel messaggio
news:aabfdi$t1a$1...@pegasus.tiscalinet.it...

Ad esempio con uno shell sort, ma credo che sia più semplice ordinarle via
via che le inserisci nella lista, visto che l'inserimento di un elemento in
qualunque punto è un'operazione immediata. In alternativa puoi usare un
albero binario, e poi fare una lettura simmetrica (che ti legge tutti gli
elementi dal + piccolo al + grande) per inserirle nel file di output.
Ciao,
Cecco


La struttura da utilizzare è un albero binario di ricerca. E' un pò
più complesso per quanto riguarda l'inserimento, ma è molto più veloce
la ricerca all'interno della struttura.
---
Massimiliano Iannotta
Università degli studi del Sannio
Informatic Engineering in progress ...

la ricerca all'interno della struttura.
Non mi sembra che lui chiedesse di implementare funzioni di ricerca.
La soluzione più semplice mi sembra un inserimento ordinato in una
lista.
Per imparare a gestire gli alberi c'è tempo, no?
Può più facilmente associare ad una lista un vettore di puntatori di
pari dimensione, e ordinarlo con un algoritmo più facile.
-- 
Cordiali saluti
  Artemio


wrote:


Il metodo più facile che mi viene in mente dalle tue parole è di
riempire una lista in maniera ordinata, e contare man mano gli
elementi inseriti.
Una volta finito di leggere il file, allochi un vettore di puntatori
al tipo di dato della tua lista
(per esempio dichiari all'inizio
struct nodo
{
  char parola[20];
  struct nodo *next;
};
puoi definire un puntatore
struct nodo *elementi;
e dopo l'inserimento, contando gli elementi con un contatore "cont",
scrivi
elementi = malloc(sizeof(struct lista) * cont);  )
Questo sarà un vettore che ti permetterà di adattare facilmente un
qualsiasi algoritmo di ordinamento sui vettori che tu conosca, facendo
un pò attenzione ai puntatori.
-- 
Cordiali saluti
  Artemio

 elementi = malloc(sizeof(struct lista) * cont);  )
?
La malloc non deve essere:
elementi = malloc(sizeof(struct nodo*) * cont);
altrimenti non ho capito bene il metodo che proponi.
Ciao,
Cecco

 Prima di tutto grazie per avermi risposto!!
Per caso puoi suggerirmi 2 righe di codice per l'ordinamento alfabetico
delle parole??
Grazie

altrimenti non ho capito bene il metodo che proponi.
Hai capito bene.
Ho dimenticato un asterisco. ;-)
-- 
Cordiali saluti
  Artemio

Grazie
Hai due strade: 
-1- realizzi da te tutte le funzioni necessarie (meglio se sei agli
inizi);
-2- usi le funzioni di libreria;
se usi le funzioni di libreria devi includere la libreria string.h
mettendo
#include <string.h>
all'inizio del sorgente.
A questo punto puoi puoi usare un qualsiasi ordinamento facile facile,
come per esempio il bubble sort.
Se per esempio
char mat_st[100][20];
è la tua matrice di stringhe e
char temp[20];
è la stringa di swap (per scambiare due elementi), per effettuare un
ordinamento alfabetico crescente scriverai:
while(!finito)  /* prosegue finché non finiscono gli scambi (matrice
ordinata) */
{
  finito = 0;
  for(i = 0; i < 100 - 1; i++) 
  {
    if(strcmp(mat_st[i], mat_st[j]) > 0)
    {
      finito = 1;  /* si ricorda che ha eseguito uno scambio*/
      strcpy(temp, mat_st[i]); /* inverte i due elementi */
      strcpy(mat_st[i], mat_st[i + 1];
      strcpy(mat_st[i + 1], temp);
    }
  }
}
Per cambiare la direzione dell'ordinamento e renderlo decrescente ti
basta mettere < nello if.
nel for ho messo la condizione i < 100 - 1 per evidenziare il fatto
che mi devo fermare un elemento prima della fine (il confronto viene
svolto sull'elemento stesso e sul successivo, quindi non voglio uscire
dalla matrice).
La funzione strcmp restituisce un numero.
dato 
num = strcmp(a, b);
dove a, b sono array di caratteri e num è un numero int, num assume
valore
positivo se a è alfabeticamente superiore a b
negativo se a è alfabeticamente inferiore a b
nullo se sono uguali.
Se poi vuoi riordinare per lunghezza, ti basta fare copia&incolla e
usare la strlen (restituisce la lunghezza della stringa in caratteri)
anziché la strcmp.
while(!finito)  /* prosegue finché non finiscono gli scambi (matrice
ordinata) */
{
  finito = 0;
  for(i = 0; i < 100 - 1; i++) 
  {
    if(strlen(mat_st[i], mat_st[j]) > 0)
    {
      finito = 1;  /* si ricorda che ha eseguito uno scambio*/
      strcpy(temp, mat_st[i]); /* inverte i due elementi */
      strcpy(mat_st[i], mat_st[i + 1];
      strcpy(mat_st[i + 1], temp);
    }
  }
}
Volendo fare le cose ancora meglio, potresti ricorrere ad una sola
funzione di ordinamento, ed usare un puntatore a funzione per le
condizioni, ma anche così dovrebbe funzionare bene.
Ma se tu sapessi già usare i puntatori a funzione, quel che ti dico ti
sembrerebbe banale, perciò usa la soluzione più facile. :-)
Non ho controllato se funzionano, quindi qualche errore può essermi
sfuggito. ;-)
Può essere un esercizio anche farne il debugging.
Ciao!
-- 
Cordiali saluti
  Artemio

}
Cazz... correzione.
intanto bisogna inizializzare
char finito = 0;
e poi correggere il suo uso nel while. Sorry, ho scritto di fretta
stamattina. :-)
while(!finito)  /* prosegue finché non finiscono gli scambi (matrice
ordinata) */
{
  finito = 1
  for(i = 0; i < 100 - 1; i++) 
  {
    if(strcmp(mat_st[i], mat_st[j]) > 0)
    {
      finito = 0  /* si ricorda che ha eseguito uno scambio*/
      strcpy(temp, mat_st[i]); /* inverte i due elementi */
      strcpy(mat_st[i], mat_st[i + 1];
      strcpy(mat_st[i + 1], temp);
    }
  }
}
-- 
Cordiali saluti
  Artemio