Recommended Posts

Hi Forum!

I write this little code, to order an array by the first line, this main's point, the first line (or line 0) have any label name, each col means a label's data.

The others is a data.

Like this (example):

+--+--+

|bb|aa|

+--+--+

|22|11|

+--+--+

Then build a array with labels (aa, bb), sort, and change the columns by the sort result:

After sort:

+--+--+

|aa|bb|

+--+--+

|11|22|

+--+--+

Someone have a best way to do this?

#include <Array.au3>

Local \$arr[] = [ _
['cField', 'aField', 'bField'], _
['333', '111', '222'] _
]

_ArrayTec(\$arr)

Func _ArrayTec(ByRef \$arr)
_ArrayDisplay(\$arr, 'before sort')
__ArrayTecSort(\$arr)
_ArrayDisplay(\$arr, 'after sort')
EndFunc   ;==>_ArrayTec

Func __ArrayTecSort(ByRef \$arr)
Local \$col[UBound(\$arr, 2)]
For \$ii = 0 To UBound(\$arr, 2) - 1
\$col[\$ii] = \$arr[\$ii]
\$col[\$ii] = \$ii
Next
Local \$old = \$col
_ArraySort(\$old, 1)
For \$ii = 0 To UBound(\$arr, 2) - 1
\$col[\$ii] = \$old[\$ii]
Next

For \$ii = 0 To UBound(\$arr, 2) - 1
_ArraySwap(\$arr, \$old[\$ii], \$old[\$ii], True)
Next
EndFunc   ;==>__ArrayTecSort

Br, Detefon!

Edited by Detefon

Visit my repository

Share on other sites

I would transpose the array (switch rows and columns) by using _ArrayTranspose, sort the array with _ArraySort and then transpose the array again.

Never tried it myxself so I don't know how fast this approach is.

My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2019-08-19 - Version 1.4.13.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX (NEW 2019-07-24 - Version 1.3.6.0) - Download - General Help & Support - Example Scripts - Wiki
Outlook Tools (NEW 2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
PowerPoint (2017-06-06 - Version 0.0.5.0) - Download - General Help & Support
Excel - Example Scripts - Wiki
Word - Wiki
Taks Scheduler (NEW 2019-10-09 - Version 0.9.0.0) - Download - General Help & Support - Wiki

Tutorials:

Share on other sites

@water, I never try _ArrayTranspose, very interesting... I will try, thank you!

Edited by Detefon

Visit my repository

Share on other sites

For small arrays does not have diference...
With small arrays, above 50 lines, is notable.

_ArraySortMethodOne(2,2)= 0.292023906830606
_ArraySortMethodTwo(2,2)= 0.191301020851811
_ArraySortMethodOne(5,2)= 0.232966962893399
_ArraySortMethodTwo(5,2)= 0.315211909358098
_ArraySortMethodOne(10,2)= 0.262676591131748
_ArraySortMethodTwo(10,2)= 0.733320579931943
_ArraySortMethodOne(50,2)= 0.230793087656447
_ArraySortMethodTwo(50,2)= 13.8305565700307
_ArraySortMethodOne(100,2)= 0.230793087656447
_ArraySortMethodTwo(100,2)= 54.7367292163035
_ArraySortMethodOne(2,5)= 0.613395129360069
_ArraySortMethodTwo(2,5)= 0.491658116090735
_ArraySortMethodOne(5,5)= 0.655785696480641
_ArraySortMethodTwo(5,5)= 0.517382306394671
_ArraySortMethodOne(10,5)= 0.571004562239497
_ArraySortMethodTwo(10,5)= 1.07715517990991
_ArraySortMethodOne(50,5)= 0.474267114195115
_ArraySortMethodTwo(50,5)= 15.1765476542437
_ArraySortMethodOne(100,5)= 0.531512495434862
_ArraySortMethodTwo(100,5)= 56.2569926320122
_ArraySortMethodOne(2,10)= 1.17896500350719
_ArraySortMethodTwo(2,10)= 1.13621212384712
_ArraySortMethodOne(5,10)= 1.30432514217144
_ArraySortMethodTwo(5,10)= 1.34236795881811
_ArraySortMethodOne(10,10)= 1.72098456258732
_ArraySortMethodTwo(10,10)= 1.66627536912402
_ArraySortMethodOne(50,10)= 1.14563224987392
_ArraySortMethodTwo(50,10)= 16.8366637101963
_ArraySortMethodOne(100,10)= 0.989113232813342
_ArraySortMethodTwo(100,10)= 61.129009350562
#include <Array.au3>
#include <File.au3>

Local \$aSize[] = [ _
[2, 2], _
[5, 2], _
[10, 2], _
[50, 2], _
[100, 2], _
[2, 5], _
[5, 5], _
[10, 5], _
[50, 5], _
[100, 5], _
[2, 10], _
[5, 10], _
[10, 10], _
[50, 10], _
[100, 10] _
]

Local \$aTest, \$aOne, \$aTwo, \$time1, \$time2, \$start

For \$ii = 0 To UBound(\$aSize, 1) - 1
\$aTest = _ArrayGenerator(\$aSize[\$ii], \$aSize[\$ii])
\$aOne = \$aTest
\$aTwo = \$aTest

\$start = TimerInit()
_ArraySortMethodOne(\$aOne)
\$time1 = TimerDiff(\$start)
ConsoleWrite("_ArraySortMethodOne(" & \$aSize[\$ii] & "," & \$aSize[\$ii] & ")= " & \$time1 & @LF)

\$start = TimerInit()
_ArraySortMethodTwo(\$aTwo)
\$time2 = TimerDiff(\$start)
ConsoleWrite("_ArraySortMethodTwo(" & \$aSize[\$ii] & "," & \$aSize[\$ii] & ")= " & \$time2 & @LF)

Next

;~ _ArraySortMethodOne(\$try1)
;~ _ArrayDisplay(\$try1, "_ArraySortMethodOne[ " & TimerDiff(\$start) & "ms ]")

;~ \$start = TimerInit()
;~ _ArraySortMethodTwo(\$try2)
;~ _ArrayDisplay(\$try2, "_ArraySortMethodOne[ " & TimerDiff(\$start) & "ms ]")

Func _ArraySortMethodTwo(ByRef \$arr)
_ArrayTranspose(\$arr)
_ArraySort(\$arr)
_ArrayTranspose(\$arr)
EndFunc   ;==>_ArraySortMethodTwo

Func _ArraySortMethodOne(ByRef \$arr)
Local \$col[UBound(\$arr, 2)]
For \$ii = 0 To UBound(\$arr, 2) - 1
\$col[\$ii] = \$arr[\$ii]
\$col[\$ii] = \$ii
Next
Local \$old = \$col
_ArraySort(\$old, 1, 0, 0, 0)
For \$ii = 0 To UBound(\$arr, 2) - 1
\$col[\$ii] = \$old[\$ii]
Next

For \$ii = 0 To UBound(\$arr, 2) - 1
_ArraySwap(\$arr, \$old[\$ii], \$old[\$ii], True)
Next
EndFunc   ;==>_ArraySortMethodOne

Func _ArrayGenerator(\$lin = 2, \$col = 2)
Local \$arr[\$lin][\$col]
For \$ii = 0 To UBound(\$arr, 1) - 1
For \$jj = 0 To UBound(\$arr, 2) - 1
Switch \$ii
Case 0
\$arr[\$ii][\$jj] = __RandomName()
Case Else
\$arr[\$ii][\$jj] = StringFormat("%06s", Random(0, 999999, 1))
EndSwitch
Next
Next
Return \$arr
EndFunc   ;==>_ArrayGenerator

Func __RandomName()
Local \$string
For \$ii = 0 To 15
\$string &= Chr(Random(65, 90, 1))
Next
Return \$string
EndFunc   ;==>__RandomName
Edited by Detefon

Visit my repository

Share on other sites

Seens to be ease of coding vs. speed My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2019-08-19 - Version 1.4.13.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX (NEW 2019-07-24 - Version 1.3.6.0) - Download - General Help & Support - Example Scripts - Wiki
Outlook Tools (NEW 2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
PowerPoint (2017-06-06 - Version 0.0.5.0) - Download - General Help & Support
Excel - Example Scripts - Wiki
Word - Wiki
Taks Scheduler (NEW 2019-10-09 - Version 0.9.0.0) - Download - General Help & Support - Wiki

Tutorials:

Share on other sites

this way should be quicker (I think) could you check?

#include <Array.au3>

Local \$arr[] = [ _
['cField', 'aField', 'bField', 'fField', 'eField', 'dField', 'gField', 'iField', 'hField'], _
['333', '111', '222', "666", "555", "444", "777", "999", "888"], _
['333', '111', '222', "666", "555", "444", "777", "999", "888"], _
['333', '111', '222', "666", "555", "444", "777", "999", "888"], _
['333', '111', '222', "666", "555", "444", "777", "999", "888"] _
]

_ArrayTec(\$arr)

Func _ArrayTec(ByRef \$arr)
_ArrayDisplay(\$arr, 'before sort')
__ArrayTecSort(\$arr)
_ArrayDisplay(\$arr, 'after sort')
EndFunc   ;==>_ArrayTec

Func __ArrayTecSort(ByRef \$arr)
Local \$aNDX[UBound(\$arr, 2)]
For \$i = 0 To UBound(\$arr, 2) - 1
\$aNDX[\$i] = \$arr[\$i] ; extract first row
\$aNDX[\$i] = \$i ; and set index pre sorting
Next
_ArraySort(\$aNDX) ; sort first row
\$aTemp = \$arr ; clone \$arr to \$aTemp
For \$i = 0 To UBound(\$arr, 1) - 1 ; scan all rows
For \$ii = 0 To UBound(\$arr, 2) - 1 ; scan all columns
\$arr[\$i][\$ii] = \$aTemp[\$i][\$aNDX[\$ii]] ; rebuild \$arr using \$aNDX as index
Next
Next
EndFunc   ;==>__ArrayTecSort

edit

used a little bigger array

Edited by Chimp

small minds discuss people average minds discuss events great minds discuss ideas.... and use AutoIt....

Share on other sites

Great idea to first sort the header row and then re-arrange the data columns My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2019-08-19 - Version 1.4.13.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX (NEW 2019-07-24 - Version 1.3.6.0) - Download - General Help & Support - Example Scripts - Wiki
Outlook Tools (NEW 2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
PowerPoint (2017-06-06 - Version 0.0.5.0) - Download - General Help & Support
Excel - Example Scripts - Wiki
Word - Wiki
Taks Scheduler (NEW 2019-10-09 - Version 0.9.0.0) - Download - General Help & Support - Wiki

Tutorials:

Share on other sites

Great idea to first sort the header row and then re-arrange the data columns thanks small minds discuss people average minds discuss events great minds discuss ideas.... and use AutoIt....

Share on other sites

I improved my first _ArrayTec...

#include <Array.au3>
#include <File.au3>

; \$aSize contain the spec's random array
; create an array with \$aSize[\$lines][\$columns]
Local \$aSize[] = [ _
[2, 2], _
[5, 2], _
[10, 2], _
[50, 2], _
[100, 2], _
[2, 5], _
[5, 5], _
[10, 5], _
[50, 5], _
[100, 5], _
[2, 10], _
[5, 10], _
[10, 10], _
[50, 10], _
[100, 10] _
]

Local \$aTest, \$time, \$start

For \$ii = 0 To UBound(\$aSize, 1) - 1
; create an array: _ArrayGenerator(\$lines, \$colums)
\$aTest = _ArrayGenerator(\$aSize[\$ii], \$aSize[\$ii])

\$start = TimerInit() ; start time of sorting
_ArrayTecSort(\$aTest)
\$time = TimerDiff(\$start) ; end time of sorting
ConsoleWrite("_ArraySortByHeader(" & \$aSize[\$ii] & "," & \$aSize[\$ii] & ")= " & \$time & "ms to sorting" & @LF)
Next

Func _ArrayTecSort(ByRef \$arr)
Local \$aIndexUnsort = __ArrayHeader(\$arr)
Local \$aIndexSort = __ArrayHeader(\$arr, 1)

Local \$aFrom
Local \$aTo
; verify is \$aFrom and \$aTo is the same postion, if yes, not nothing
; verify if \$aTo[?] is in \$aFrom[?], if yes, not nothing
; verify if \$aFrom[?] is in \$aTo[?], if yes, not nothing
For \$ii = 0 To UBound(\$arr, 2) - 1
If Not (\$aIndexSort[\$ii] == \$aIndexUnsort[\$ii]) And (_ArraySearch(\$aFrom, \$aIndexSort[\$ii]) == -1) And (_ArraySearch(\$aTo, \$aIndexUnsort[\$ii]) == -1) Then
_ArrayAdd(\$aFrom, _ArraySearch(\$arr, \$aIndexUnsort[\$ii], 0, 0, 0, 0, 0, 0, True))
_ArrayAdd(\$aTo, _ArraySearch(\$arr, \$aIndexSort[\$ii], 0, 0, 0, 0, 0, 0, True))
EndIf
Next
For \$ii = 1 To UBound(\$aFrom, 1) - 1
_ArraySwap(\$arr, \$aFrom[\$ii], \$aTo[\$ii], True)
Next

Func __ArrayHeader(\$arr, \$mode = 0)
Local \$ret
For \$ii = 0 To UBound(\$arr, 2) - 1
Next
_ArrayDelete(\$ret, 0)
If \$mode Then _ArraySort(\$ret)
Return \$ret

Func _ArrayGenerator(\$lin = 2, \$col = 2)
Local \$arr[\$lin][\$col]
For \$ii = 0 To UBound(\$arr, 1) - 1
For \$jj = 0 To UBound(\$arr, 2) - 1
Switch \$ii
Case 0
\$arr[\$ii][\$jj] = __RandomName()
Case Else
\$arr[\$ii][\$jj] = StringFormat("%06s", Random(0, 999999, 1))
EndSwitch
Next
Next
Return \$arr
EndFunc   ;==>_ArrayGenerator

Func __RandomName()
Local \$string
For \$ii = 0 To 15
\$string &= Chr(Random(65, 90, 1))
Next
Return \$string
EndFunc   ;==>__RandomName
Edited by Detefon

Visit my repository

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account