Jump to content
Sign in to follow this  
Blitzkid

Filter for _FileListToArray

Recommended Posts

Hello, i want to search several directories for files with the largest numbers behind them (Like "video123") . They dont have a datatype. But there are also files with longer names and datatypes in these folders (Like "video778.mp4"). Is it possible to filter the _FileListToArray Syntax from

Quote

_FileListToArray($filedir & $arr[$i], $arr[$i] & "*", 1)

to smth. like

Quote

_FileListToArray($filedir & $arr[$i], $arr[$i] & " 3 Numbers", 1)

 

Here is my Code

#include <ButtonConstants.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <array.au3>
#include <File.au3>

$filedir = @ScriptDir & "\"
_checkfile()

Func _checkfile()
    ConsoleWrite("______________________" & @CRLF)
    Local $arr[3] = ["music", "picture", "video"]

    For $i = 0 To UBound($arr) - 1
        Local $arrayfiles = _FileListToArray($filedir & $arr[$i], $arr[$i] & "*", 1)
        If @error = 1 Then
            ConsoleWrite($arr[$i] & "Error 1")
        EndIf
        If @error = 4 Then
            ConsoleWrite($arr[$i] & "Error 2")
            ;Exit
        EndIf
        $arrayfilter = _ArrayMax($arrayfiles, 0, 1)
        Global $stringfiles = StringReplace($arrayfilter, $arr[$i], "")
        ConsoleWrite($arrayfilter & @CRLF)
    Next
EndFunc   ;==>_checkfile

 

Edited by Blitzkid

Share this post


Link to post
Share on other sites

Yes, you'll just need to loop through your array to strip out the music/picture/video text before getting the max...

; Strip out the current file prefix
For $f = 0 To UBound($arrayFiles) - 1
    $arrayFiles[$f] = StringReplace($arrayFiles[$f], $arr[$i], "")
Next

; Get the max
$arrayfilter = _ArrayMax($arrayFiles, 0, 1)

; Put the prefix back
$arrayfilter = $arr[$i] & $arrayfilter

All my code provided is Public Domain... but it may not work. ;) Use it, change it, break it, whatever you want.

Spoiler

My Humble Contributions:
Personal Function Documentation - A personal HelpFile for your functions
Acro.au3 UDF - Automating Acrobat Pro
ToDo Finder - Find #ToDo: lines in your scripts

Share this post


Link to post
Share on other sites
1 hour ago, seadoggie01 said:

Yes, you'll just need to loop through your array to strip out the music/picture/video text before getting the max...

; Strip out the current file prefix
For $f = 0 To UBound($arrayFiles) - 1
    $arrayFiles[$f] = StringReplace($arrayFiles[$f], $arr[$i], "")
Next

; Get the max
$arrayfilter = _ArrayMax($arrayFiles, 0, 1)

; Put the prefix back
$arrayfilter = $arr[$i] & $arrayfilter

Thx for the fast reply, but my problem is that i only need the files with the name f.e. video544 (always 3 numbers behind it). There are also files like video737.mp4 included. But i dont need them, but when i search for the maxnumber i'll always get the one with .mp4 in the end, instead of f.e. video544.... I need a solution that replace the "*" filter in _FileListToArray to something like "3 numbers"...

Share this post


Link to post
Share on other sites

> I need a solution that replace the "*" filter in _FileListToArray to something like "3 numbers"...

Maybe  "???" instead of  "*".  I think this will work. Not exactly what you want, but closer ("videoABC" will also be found)

Ajag

 

Edited by ajag

Rule #1: Always do a backup         Rule #2: Always do a backup (backup of rule #1)

Share this post


Link to post
Share on other sites
2 minutes ago, ajag said:

> I need a solution that replace the "*" filter in _FileListToArray to something like "3 numbers"...

Maybe  "???" instead of  "*".  I think this will work. Not exactly what you want, but closer ("videoABC" will also be found)

Ajag

 

Yes ??? is a option, but it includes letters aswell, is there a filter that includes only numbers?

Share this post


Link to post
Share on other sites

To ignore non-numbers, just wrap it in Number(), it returns 0 when the value isn't a number, so it will never be the max :)

; Strip out the current file prefix
For $f = 0 To UBound($arrayFiles) - 1
    $arrayFiles[$f] = Number(StringReplace($arrayFiles[$f], $arr[$i], ""))
Next

; Get the max
$arrayfilter = _ArrayMax($arrayFiles, 1, 1)

; Put the prefix back
$arrayfilter = $arr[$i] & $arrayfilter
Edited by seadoggie01
ArrayMax should get largest integer, not character

All my code provided is Public Domain... but it may not work. ;) Use it, change it, break it, whatever you want.

Spoiler

My Humble Contributions:
Personal Function Documentation - A personal HelpFile for your functions
Acro.au3 UDF - Automating Acrobat Pro
ToDo Finder - Find #ToDo: lines in your scripts

Share this post


Link to post
Share on other sites
2 minutes ago, seadoggie01 said:

To ignore non-numbers, just wrap it in Number(), it returns 0 when the value isn't a number, so it will never be the max :)

; Strip out the current file prefix
For $f = 0 To UBound($arrayFiles) - 1
    $arrayFiles[$f] = Number(StringReplace($arrayFiles[$f], $arr[$i], ""))
Next

; Get the max
$arrayfilter = _ArrayMax($arrayFiles, 0, 1)

; Put the prefix back
$arrayfilter = $arr[$i] & $arrayfilter

This sounds good, i'll test it out tomorrow and update this post :)

Share this post


Link to post
Share on other sites
16 hours ago, Blitzkid said:

I need a solution that replace the "*" filter in _FileListToArray to something like "3 numbers"...

It is, as far as I know, not possible to use a regular expression as a filter in _FileListToArray(Rec).

Here is a variation with FileFindFirstFile and FileFindNextFile (will also match video001). I moved the array from the function to the global scope too.

In the attachment you will find a Zip with test files (dummies only). Like in your script the subfolders \music , \picture and \video are used.

#include <File.au3>

Global $g_sFileDir
Global $g_aArr[3] = ["music", "picture", "video"]

For $i = 0 To UBound($g_aArr) - 1
    $g_sFileDir = @ScriptDir & "\" & $g_aArr[$i] & "\"
    ConsoleWrite("< "& $g_aArr[$i] & " -> highest number = " & _GetFileHighNum($g_sFileDir, $g_aArr[$i]) & @CRLF)
Next

; ---------------------------------------------------------------------
Func _GetFileHighNum($sFileDir, $sSearchName)
    Local $hSearch, $sCurrentFile, $iMaxNum = 0, $iNum = 0
    $hSearch = FileFindFirstFile($sFileDir & $sSearchName & '*')
    If $hSearch = -1 Then Return 0
    While 1
        $sCurrentFile = FileFindNextFile($hSearch)
        If @error Then
            FileClose($hSearch)
            Return $iMaxNum
        EndIf
        If StringRegExp($sCurrentFile, '(?i)^' & $sSearchName & '\d{3}$') Then
            $iNum = Number(StringRegExpReplace($sCurrentFile, '\D', ''))
            If (Not @error) And ($iNum >= $iMaxNum) Then $iMaxNum = $iNum
        EndIf
    WEnd
EndFunc   ;==>_GetFileHighNum

TestFolders.zip

Edited by Musashi
moved FileClose($hSearch) to if @error

Musashi-C64.png

"In the beginning the Universe was created. This has made a lot of people very angry and been widely regarded as a bad move."

Share this post


Link to post
Share on other sites
8 hours ago, Musashi said:

It is, as far as I know, not possible to use a regular expression as a filter in _FileListToArray(Rec).

Here is a variation with FileFindFirstFile and FileFindNextFile (will also match video001). I moved the array from the function to the global scope too.

In the attachment you will find a Zip with test files (dummies only). Like in your script the subfolders \music , \picture and \video are used.

#include <File.au3>

Global $g_sFileDir
Global $g_aArr[3] = ["music", "picture", "video"]

For $i = 0 To UBound($g_aArr) - 1
    $g_sFileDir = @ScriptDir & "\" & $g_aArr[$i] & "\"
    ConsoleWrite("< "& $g_aArr[$i] & " -> highest number = " & _GetFileHighNum($g_sFileDir, $g_aArr[$i]) & @CRLF)
Next

; ---------------------------------------------------------------------
Func _GetFileHighNum($sFileDir, $sSearchName)
    Local $hSearch, $sCurrentFile, $iMaxNum = 0, $iNum = 0
    $hSearch = FileFindFirstFile($sFileDir & $sSearchName & '*')
    If $hSearch = -1 Then Return 0
    While 1
        $sCurrentFile = FileFindNextFile($hSearch)
        If @error Then Return $iMaxNum
        If StringRegExp($sCurrentFile, '(?i)^' & $sSearchName & '\d{3}$') Then
            $iNum = Number(StringRegExpReplace($sCurrentFile, '\D', ''))
            If (Not @error) And ($iNum >= $iMaxNum) Then $iMaxNum = $iNum
        EndIf
    WEnd
    FileClose($hSearch)
EndFunc   ;==>_GetFileHighNum

TestFolders.zip 3.19 kB · 0 downloads

Thats exactly what i needed, thank you very much ♥

Also big thank you to @seadoggie01 and @ajag

Edited by Blitzkid

Share this post


Link to post
Share on other sites
5 minutes ago, Blitzkid said:

Thats exactly what i needed, thank you very much ♥

You are welcome 🙂.

I have made one minor change : FileClose($hSearch) was moved from the end of the function behind if @error... (view my code sample above), because I leave the while loop with Return, not with ExitLoop.


Musashi-C64.png

"In the beginning the Universe was created. This has made a lot of people very angry and been widely regarded as a bad move."

Share this post


Link to post
Share on other sites

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

Sign in

Already have an account? Sign in here.

Sign In Now
Sign in to follow this  

  • Recently Browsing   0 members

    No registered users viewing this page.

  • Similar Content

    • By vinnyMS
      #Include <Array.au3> #include <Constants.au3> $s = FileRead("2.txt") Local $w = StringRegExp($s, '(?is)(\b\w+\b)(?!.*\b\1\b)', 3) _ArrayColInsert($w, 1) For $i = 0 to UBound($w)-1 StringRegExpReplace($s, '(?i)\b' & $w[$i][0] & '\b', $w[$i][0]) $w[$i][1] = @extended Next _ArraySort($w, 1, 0, 0, 1) _ArrayDisplay($w) i have this script that returns 3 columns  
       
      i need to copy the  Col 0 and Col 1 as text to paste on notepad or excel
      you will have to create a "copy" button if possible
      array.au3 2.txt
    • By DannyJ
      I have a dataset like this, (a strubg)
      Username: User1 Type: Admin RegDate: 1999 Username: User2 Type: User RegDate: 2000 How to make a 2 dimensional array that I can display with _ArrayDisplay?
      This would be a perfect 2D array to represent my data:
      Username           Tpye RegDate User1              Admin 1999 User2              User 2000   If you run this Powershell this powershell command, you can get this dataset that I am talking about:
      Get-LocalUser | Select * With this code you can try it to read into a string:
      #include <GuiConstantsEx.au3> #include <WindowsConstants.au3> #include "GUIListViewEx.au3" #include <Array.au3> ; Just for display in example #RequireAdmin #Region ;**** Directives created by AutoIt3Wrapper_GUI **** #AutoIt3Wrapper_UseX64=y #EndRegion $sCommand = "powershell.exe Get-LocalUser | Select *" Local $iPid = Run($sCommand, @WorkingDir , @SW_SHOW , $STDOUT_CHILD) ProcessWaitClose($iPid) Local $sOutput = StdoutRead($iPID) ConsoleWrite($sOutput) How can I correctly split $sOutput into a 2D array (with the above mentioned layout) that I can display and I work with?
    • By kovlad
      My solution is to write nested arrays without copying.
      The problem was described hier.
       
      Function:
      #include <Array.au3> ; #FUNCTION# ==================================================================================================================== ; Name ..........: _ArrayNestedSet ; Description ...: Assigns a value to an element of a nested 1D array. ; Syntax ........: _ArrayNestedSet(ByRef $aArray, $vIndex, $vValue) ; Parameters ....: $aArray - an array of arrays. ; $vIndex - an index or 1d-array of indexes; ; a size if $vValue not defined (zero to delete). ; $vValue - a value (create, resize or delete if not defined). ; ; Return values .: on success - 1 ; @extended - nesting level of operation ; on failure - 0 ; @extended - nesting level of error ; @error = 1 - invalid array ; @error = 2 - invalid index ; Author ........: ; Modified ......: kovlad ; Remarks .......: ; Related .......: ; Link ..........: https://www.autoitscript.com/forum/topic/185638-assign-a-value-to-an-array-in-array-element/ ; https://www.autoitscript.com/trac/autoit/ticket/3515?replyto=description ; Example .......: Yes ; =============================================================================================================================== Func _ArrayNestedSet(ByRef $aArray, $vIndex, $vValue = Default) Local $extended = @extended + 1 If IsArray($vIndex) Then If UBound($vIndex, 0) <> 1 Then _ Return SetError(2, $extended) If UBound($vIndex) > 1 Then If UBound($aArray, 0) <> 1 Then _ Return SetError(1, $extended) ; keep index for this array Local $i = $vIndex[0] If $i < 0 Or UBound($aArray) <= $i Then _ Return SetError(2, $extended) ; delete index of this array _ArrayDelete($vIndex, 0) ; recursive function call Local $return = _ArrayNestedSet($aArray[$i], $vIndex, $vValue) If @error Then Return SetError(@error, @extended + 1, 0) Else Return SetExtended(@extended + 1, 1) EndIf Else $vIndex = $vIndex[0] EndIf EndIf If $vValue = Default Then If $vIndex < 0 Then _ Return SetError(2, $extended) If $vIndex = 0 Then ; delete array and free memory $aArray = 0 Return SetExtended($extended, 1) EndIf If UBound($aArray, 0) = 1 Then ; resize array keeping data ReDim $aArray[$vIndex] Return SetExtended($extended, 1) Else ; create new nested array Local $aTmp[$vIndex] $aArray = $aTmp Return SetExtended($extended, 1) EndIf Else If UBound($aArray) <= $vIndex Then _ Return SetError(2, $extended + 1) ; set value of array entry $aArray[$vIndex] = $vValue Return SetExtended($extended, 1) EndIf EndFunc  
      Examples:
      ; write value to 1st nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : write value to 1st nested array" & @CRLF) Local $aTmp1[4] = [1,2,3,4] _ArrayDisplay($aTmp1, "$aTmp1") Local $aArray[2] = [$aTmp1] ConsoleWrite( _ "_ArrayNestedSet($aArray[0], 3, 14) = " & _ArrayNestedSet($aArray[0], 3, 14) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay($aArray[0], "$aArray[0]") ; resize 1st nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : resize 1st nested array" & @CRLF) ConsoleWrite( _ "_ArrayNestedSet($aArray[0], 8) = " & _ArrayNestedSet($aArray[0], 8) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay($aArray[0], "$aArray[0]") ; write array to 1st nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : write array to 1st nested array" & @CRLF) Local $aTmp11[4] = [11,12,13,14] _ArrayDisplay($aTmp11, "$aTmp11") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], 2, $aTmp11) = " & _ArrayNestedSet($aArray[0], 2, $aTmp11) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay(($aArray[0])[2], "($aArray[0])[2]") ; write value to 2nd nested array using index array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : write value to 2nd nested array using index array" & @CRLF) Local $aIndex1[2] = [2,3] _ArrayDisplay($aIndex1, "$aIndex1") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex1, 140) = " & _ArrayNestedSet($aArray[0], $aIndex1, 140) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay(($aArray[0])[2], "($aArray[0])[2]") ; resize 2nd nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : resize 2nd nested array" & @CRLF) Local $aIndex1[2] = [2,8] _ArrayDisplay($aIndex1, "$aIndex1") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex1) = " & _ArrayNestedSet($aArray[0], $aIndex1) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay(($aArray[0])[2], "($aArray[0])[2]") ; create new 3rd nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : create new 3rd nested array" & @CRLF) Local $aIndex2[3] = [2,7,6] _ArrayDisplay($aIndex2, "$aIndex2") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex2) = " & _ArrayNestedSet($aArray[0], $aIndex2) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF & @CRLF) _ArrayDisplay((($aArray[0])[2])[7], ")($aArray[0])[2])[7]") ; delete 3rd nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : delete 3rd nested array" & @CRLF) Local $aIndex3[3] = [2,7,0] _ArrayDisplay($aIndex3, "$aIndex2") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex3) = " & _ArrayNestedSet($aArray[0], $aIndex3) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF) ConsoleWrite("IsArray((($aArray[0])[2])[7]) = " & IsArray((($aArray[0])[2])[7]) & @CRLF & @CRLF) ; write 0 in 1st nested array to delete the 2nd nested array ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : write 0 in 1st nested array to delete the 2nd nested array" & @CRLF) Local $aIndex4[1] = [2] _ArrayDisplay($aIndex4, "$aIndex4") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex4, 0) = " & _ArrayNestedSet($aArray[0], $aIndex4, 0) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF) ConsoleWrite("IsArray(($aArray[0])[2]) = " & IsArray(($aArray[0])[2]) & @CRLF & @CRLF) ; delete 1st nested array (same as '$aArray[0] = 0') ConsoleWrite("@@ Debug(" & @ScriptLineNumber & ") : delete 1st nested array (same as '$aArray[0] = 0')" & @CRLF) Local $aIndex5[1] = [0] _ArrayDisplay($aIndex5, "$aIndex5") ConsoleWrite( _ "_ArrayNestedSet($aArray[0], $aIndex5) = " & _ArrayNestedSet($aArray[0], $aIndex5) & @CRLF & _ " @error = " & @error & @CRLF & _ " @extended = " & @extended & @CRLF) ConsoleWrite("IsArray($aArray[0]) = " & IsArray($aArray[0]) & @CRLF & @CRLF)  
    • By DannyJ
      $sCommands1 = 'powershell.exe Get-ChildItem' $iPid = run($sCommands1   , @WorkingDir , @SW_SHOW , 0x2) $sOutput = ""  While 1     $sOutput &= StdoutRead($iPID)         If @error Then             ExitLoop         EndIf  WEnd ;~ msgbox(0, '' , $sOutput) ConsoleWrite("$sOutput") ConsoleWrite($sOutput) ConsoleWrite(@CRLF) $aOutput = stringsplit($sOutput ,@LF , 2) For $i=0 To  UBound($aOutput) - 1 Step 1     ConsoleWrite($aOutput[$i]) Next The script above reads the whole directory into a one dimensional array, but I need to work with the array, so I need to split the array into multiple dimensions.
      I have already read some forum answers here, and I have already tried these commands:
       
      Are there any way to use the $aOutput variable like in PowerShell:
      PowerShell:
      $a = Get-ChildItem $a.Mode I imagine this in AutoIt  $aOutput
      ConsoleWrite($aOutput[i].Mode) Or if I split this command into 2 dimension like:
      For $i To UBound($aOutput)-1 Step 1 ConsoleWrite($aOutput[$i][1]) ConsoleWrite($aOutput[$i][2]) Next  
    • By Mannyfresh31
      Please help with this 3D Array the first example works the secound doesn't.
      Need help to understand how Arrays work.
      Many thanks in advance
      ;First Example Dim $aArray[2][2][2] $aArray[0][0][0] = 1 $aArray[0][0][1] = 2 $aArray[0][1][0] = 3 $aArray[0][1][1] = 4 $aArray[1][0][0] = 5 $aArray[1][0][1] = 6 $aArray[1][1][0] = 7 $aArray[1][1][1] = 8 For $a = 0 to 1 for $b = 0 to 1 for $c = 0 to 1 ConsoleWrite($aArray[$a][$b][$c] & @CRLF) Next Next Next ;Secound Example Local $aArraym [2][2][2]=[[[1,2,],[3,4],[5,6],[7,8]]] For $a = 0 to 1 for $b = 0 to 1 for $c = 0 to 1 ConsoleWrite($aArraym[$a][$b][$c] & @CRLF) Next Next Next  
×
×
  • Create New...