Re: Sort Multidimensional Array by Column 5
Re: Sort Multidimensional Array by Column 5
- Subject: Re: Sort Multidimensional Array by Column 5
- From: KOENIG Yvan <email@hidden>
- Date: Fri, 8 Oct 2010 12:12:45 +0200
--[SCRIPT]
(* Tri par interclassement
--> renvoie une copie triée de la liste originale.
Implémentation: L. Sebilleau & D. Varlet
*)
on intersort(laListe, fcmp)
-- le deuxième paramètre est un pointeur sur la fonction de comparaison à employer
script lstock -- l'intérêt de ce script est d'accélérer le traitement des listes
property listeorg : laListe
property liste1 : {}
property liste2 : {}
property listea : {}
property listeb : {}
property lister : {}
property Compare : fcmp -- ce pointeur de fonction est stocké là
end script
-- répartition des éléments à trier en sous-listes de longueur deux
tell lstock
set ct to (its listeorg)'s length
set flag to false
if (ct mod 2) = 1 then
set ct to ct - 1
set flag to true
end if
repeat with i from 1 to ct by 2
set x to item i of its listeorg
set y to item (i + 1) of its listeorg
if Compare(x, y) then -- la fonction de comparaison est employée ici
{x, y}
else
{y, x}
end if
set the end of its liste1 to result
end repeat
if flag then set the end of its liste1 to {item -1 of its listeorg}
-- interclassement des listes contenues dans liste1
repeat
set ct to (its liste1)'s length
if ct = 1 then exit repeat -- tant qu'il me reste plusieurs listes, c'est pas fini
set flag to false
if (ct mod 2) = 1 then
set ct to ct - 1
set flag to true
end if
set its liste2 to {}
repeat with i from 1 to ct by 2 -- on prend les listes 2 par 2
set its listea to item i of its liste1
set its listeb to item (i + 1) of its liste1
set its lister to {} -- pour n'en faire qu'une seule dans celle-là
set cta to (its listea)'s length
set ctb to (its listeb)'s length
set ya to 1
set yb to 1
repeat
-- la fonction de comparaison est aussi employée ici:
if Compare(item yb of its listeb, item ya of its listea) then -- comparaison des premiers éléments
set the end of its lister to (item yb of its listeb) -- "extraction" du premier
set yb to yb + 1
if yb > ctb then -- si cette liste est maintenant vide, on arrête là.
if ya ≤ cta then -- il peut rester des éléments dans l'une des listes
set its lister to (its lister) & (items ya thru -1 of its listea)
end if
exit repeat
end if
else -- symétrique dans le cas inverse
set the end of its lister to (item ya of its listea)
set ya to ya + 1
if ya > cta then
if yb ≤ ctb then -- il peut rester des éléments dans l'une des listes
set its lister to (its lister) & (items yb thru -1 of its listeb)
end if
exit repeat
end if
end if
end repeat
-- la nouvelle liste produite par la fusion est ajoutée en tant que liste au résultat
set the end of its liste2 to its lister
end repeat -- et on recommence tant qu'il reste des paires de listes
-- sans oublier l'orpheline si le nombre de listes est impair: on l'ajoute simplement à la fin
if flag then set the end of its liste2 to {} & item -1 of its liste1
set its liste1 to its liste2 -- et c'est reparti pour un tour
end repeat
return first item of its liste1 -- parce que c'est une liste de listes, même si elle n'en contient plus qu'une seule
end tell
end intersort
----------- les fonctions de comparaison ------------
on cmpasc(n1, n2) -- pour le tri ascendant des nombres et des chaînes
return n1 < n2
end cmpasc
on cmpdesc(n1, n2) -- tri descendant des nombres et des chaînes
return n1 > n2
end cmpdesc
on recmp(n1, n2) -- tri par noms
return (nom of n1 < nom of n2)
end recmp
on agecmp(n1, n2) -- tri par âges
return (Age of n1 < Age of n2)
end agecmp
on cmpdesc5(n1, n2) -- tri descendant des nombres et des chaînes
return (item 5 of n1) > (item 5 of n2)
end cmpdesc5
---------------- Pour tester ----------------
on run
set le_fichier to "" & (path to desktop) & "uncsv.csv"
set une_liste to paragraphs of (read file le_fichier)
set the_headers to item 1 of une_liste
repeat with une_ref in une_liste
set contents of une_ref to my decoupe(text 2 thru -2 of contents of une_ref, quote & "," & quote)
end repeat
set ma_Liste to my intersort(items 2 thru -1 of une_liste, my cmpdesc5)
repeat with one_row in ma_Liste
set contents of one_row to quote & my recolle(contents of one_row, quote & "," & quote) & quote
end repeat
set sLOGdata to the_headers & return & my recolle(ma_Liste, return)
(* now you may save the text datas *)
set target_file to (do shell script "date +%Y%m%d_%H%M%S.csv")
set p2d to path to desktop
tell application "System Events" to make new file at end of p2d with properties {name:target_file}
write sLOGdata to file ("" & p2d & target_file)
end run
--=====
on decoupe(t, d)
local oTIDs, l
set oTIDs to AppleScript's text item delimiters
set AppleScript's text item delimiters to d
set l to text items of t
set AppleScript's text item delimiters to oTIDs
return l
end decoupe
--=====
on recolle(l, d)
local oTIDs, t
set oTIDs to AppleScript's text item delimiters
set AppleScript's text item delimiters to d
set t to l as text
set AppleScript's text item delimiters to oTIDs
return t
end recolle
--=====
--[/SCRIPT]
This one reads the csv, sort its contents and save the sorted datas.
Here I save in a new file.
Adjust the code to fit your own needs.
Yvan KOENIG (VALLAURIS, France) vendredi 8 octobre 2010 12:11:07
_______________________________________________
Do not post admin requests to the list. They will be ignored.
AppleScript-Users mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
Archives: http://lists.apple.com/archives/applescript-users
This email sent to email@hidden