GNU/Linux >> Linux Esercitazione >  >> Linux

Stai cercando di ordinare su due campi, il secondo e il primo?

Sto cercando di ordinare su più colonne. I risultati non sono quelli previsti.

Ecco i miei dati (people.txt):

Simon Strange 62
Pete Brown 37
Mark Brown 46
Stefan Heinz 52
Tony Bedford 50
John Strange 51
Fred Bloggs 22
James Bedford 21
Emily Bedford 18
Ana Villamor 44
Alice Villamor 50
Francis Chepstow 56

Quanto segue funziona correttamente:

bash-3.2$ sort -k2 -k3 <people.txt                                                                                                                    
Emily Bedford 18                                                                                                                                      
James Bedford 21                                                                                                                                      
Tony Bedford 50                                                                                                                                       
Fred Bloggs 22                                                                                                                                        
Pete Brown 37                                                                                                                                         
Mark Brown 46                                                                                                                                         
Francis Chepstow 56                                                                                                                                   
Stefan Heinz 52                                                                                                                                       
John Strange 51                                                                                                                                       
Simon Strange 62                                                                                                                                      
Ana Villamor 44                                                                                                                                       
Alice Villamor 50

Ma quanto segue non funziona come previsto:

bash-3.2$ sort -k2 -k1 <people.txt                                        
Emily Bedford 18                                                                                                                                      
James Bedford 21                                                                                                                                      
Tony Bedford 50                                                                                                                                       
Fred Bloggs 22                                                                                                                                        
Pete Brown 37                                                                                                                                         
Mark Brown 46                                                                                                                                         
Francis Chepstow 56                                                                                                                                   
Stefan Heinz 52                                                                                                                                       
John Strange 51                                                                                                                                       
Simon Strange 62                                                                                                                                      
Ana Villamor 44                                                                                                                                       
Alice Villamor 50

Stavo cercando di ordinare per cognome e poi per nome, ma vedrai che i Villamor non sono nell'ordine corretto. Speravo di ordinare per cognome e poi, quando i cognomi corrispondevano, di ordinare per nome.

Sembra che ci sia qualcosa su come dovrebbe funzionare che non capisco. Ovviamente potrei farlo in un altro modo (usando awk), ma voglio capire l'ordinamento.

Sto usando la shell Bash standard su Mac OS X.

Risposta accettata:

Una specifica chiave come -k2 significa prendere in considerazione tutti i campi da 2 a fine riga. Quindi Villamor 44 finisce prima di Villamor 50 . Poiché questi due non sono uguali, il primo confronto in sort -k2 -k1 è sufficiente per discriminare queste due righe, e la seconda chiave di ordinamento -k1 non è invocato. Se i due Villamor avessero avuto la stessa età, -k1 li avrebbe ordinati per nome.

Per ordinare in base a una singola colonna, usa -k2,2 come specifica chiave. Ciò significa utilizzare i campi dal n. 2 al n. 2, ovvero solo il secondo campo.

sort -k2 -k3 <people.txt è ridondante:equivale a sort -k2 <people.txt . Per ordinare in base ai cognomi, quindi ai nomi, quindi all'età, esegui il comando seguente:

sort -k2,2 -k1,1 <people.txt

o equivalentemente sort -k2,2 -k1 <people.txt poiché ci sono solo questi tre campi e i separatori sono gli stessi. In effetti, otterrai lo stesso effetto da sort -k2,2 <people.txt , perché sort utilizza l'intera riga come ultima risorsa quando tutte le chiavi in ​​un sottoinsieme di righe sono identiche.

Correlati:come cercare il testo in un file e visualizzare il paragrafo che contiene il testo?

Nota inoltre che il separatore di campo predefinito è la transizione tra uno spazio non vuoto e uno spazio vuoto, quindi le chiavi includeranno gli spazi vuoti iniziali (nel tuo esempio, per la prima riga, la prima chiave sarà "Emily" , ma la seconda chiave " Bedford" . Aggiungi il -b opzione per rimuovere quegli spazi vuoti:

sort -b -k2,2 -k1,1

Può anche essere fatto per chiave aggiungendo il b flag alla fine della specifica di avvio chiave:

sort -k2b,2 -k1,1 <people.txt

Ma qualcosa da tenere a mente:non appena aggiungi uno di questi flag alla specifica della chiave, i flag globali (come -n , -r ...) non si applicano più a loro, quindi è meglio evitare di mescolare i flag per chiave e i flag globali.


Linux
  1. Come fare A Ls e quindi ordinare i risultati per data di creazione?

  2. Passare a una seconda sessione X uccide la prima?

  3. Ordina per valore esadecimale?

  4. Ordinare parte di un file?

  5. Lum:sostituire i valori comuni in due file in base alla prima colonna?

File di ordinamento della shell Linux in base alla seconda colonna?

Confrontando due elenchi non ordinati in Linux, elencando l'univoco nel secondo file

Come posso ottenere parole tra le prime due istanze di testo/modello?

Come posso fare in modo che ls mostri prima i dotfile?

Come posso scambiare il primo e il secondo flusso audio in un MKV in un sistema basato su Linux?

Come ordinare i risultati dal comando ls per data di modifica (prima le directory)?