Jump to content

copying all doc files from a folder


 Share

Recommended Posts

Hi !

I am new to AutoIt and this is my first post !

I need a help in accomplishing the following:

I have a folder containing many subfolders. Inside them many different files. I want to copy all *.doc and *.docx files using autoit into a new folder.

Your help is appreciated.

Link to comment
Share on other sites

Questions:

1) Do you want to retain the original directory structure?

2) Have you used the search function and/or Google? This has been done before :) What have you tried?

3) Are you sure you need (or want to use) AutoIt? A quick robocopy (robocopy <source-dir> <destination-dir> *.doc *.docx /s) or a nice Powershell oneliner seems easier.

If you want to use AutoIt, check out _FileListToArrayRec and FileCopy.

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

Prompt response. Thanks!

1. Not necesssary, but in case of I didn't retain the original directory structure and I got duplicated, this is the only problem.

2. I did but didn't get what I wanted.

3. Using another tool does not suit my need because will using that code in a loop.

 

Thanks

Link to comment
Share on other sites

  • Moderators

@Sarah2016 something like this perhaps:

#include <File.au3>

Local $aFolders = _FileListToArrayRec(@ScriptDir & "\1", "*", $FLTAR_FOLDERS, $FLTAR_RECUR, $FLTAR_SORT, $FLTAR_FULLPATH)
    For $a = 1 To $aFolders[0]
        FileCopy($aFolders[$a] & "\*.docx", @TempDir & "\*.docx", 1)
    Next

assuming my file structure is 1 (top level), 2,3,4 all subfolders of one. This will pull any .docx file from any of them and put it into the temp directory. I suggest looking into both the _FileListToArrayRec and FileCopy subjects in the help file and trying to modify this to fit your needs. Feel free to ask questions if you run into issues.

Edit: Welcome to the forum, btw

Edited by JLogan3o13

"Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball

How to get your question answered on this forum!

Link to comment
Share on other sites

8 minutes ago, JLogan3o13 said:

@Sarah2016 something like this perhaps:

#include <File.au3>

Local $aFolders = _FileListToArrayRec(@ScriptDir & "\1", "*", $FLTAR_FOLDERS, $FLTAR_RECUR, $FLTAR_SORT, $FLTAR_FULLPATH)
    For $a = 1 To $aFolders[0]
        FileCopy($aFolders[$a] & "\*.docx", @TempDir & "\*.docx", 1)
    Next

assuming my file structure is 1 (top level), 2,3,4 all subfolders of one. This will pull any .docx file from any of them and put it into the temp directory. I suggest looking into both the _FileListToArrayRec and FileCopy subjects in the help file and trying to modify this to fit your needs. Feel free to ask questions if you run into issues.

Edit: Welcome to the forum, btw

Fantastic!

1 problem: this code only copies .docx files, how to include .doc as well?

Link to comment
Share on other sites

  • Moderators

Look at the remarks under FileCopy. You should be able to wildcard the extension, something like this:

FileCopy($aFolders[$a] & "\*.doc*", @TempDir, 1)

 

"Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball

How to get your question answered on this forum!

Link to comment
Share on other sites

The easiest solution would be to simply repeat the FileCopy with different filespecs. One could also consider specifying the second parameter in the _FileListToArrayRec function call (the $sMask), as it allows multiple filters separated by ;

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

21 minutes ago, SadBunny said:

The easiest solution would be to simply repeat the FileCopy with different filespecs. One could also consider specifying the second parameter in the _FileListToArrayRec function call (the $sMask), as it allows multiple filters separated by ;

thanks, but the second option you mentioned does not seem to work because the _filelisttoarrayrec will retrieve FOLDERS list not files.. Am I right?

Link to comment
Share on other sites

Have you read the help file for _FileListToArrayRec? (I know it's not the easiest command to understand if you're writing your first script, but the help file is very informative :) )

Read the bit about $iReturn - you can specify whether to return a list of files, a list of folders or a list of both files and folders.

Change the $FLTAR_FOLDERS in Logan's example to $FLTAR_FILES or $FLTAR_FILESFOLDERS and it will return the respective information.

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

I created a test dir:

Quote

c:\tmp\test>dir /s /b
c:\tmp\test\1
c:\tmp\test\2
c:\tmp\test\3
c:\tmp\test\1\x.docx
c:\tmp\test\1\y.doc
c:\tmp\test\2\x.txt
c:\tmp\test\2\y.doc

And here's another example snippet:

#include <File.au3>

Local $aFolders = _FileListToArrayRec("c:\tmp\test", "*.doc;*.docx", $FLTAR_FILES, $FLTAR_RECUR, $FLTAR_SORT, $FLTAR_FULLPATH)
For $a = 1 To $aFolders[0]
    ConsoleWrite($aFolders[$a] & @CRLF)
Next

The console outputs:

Quote

c:\tmp\test\1\x.docx
c:\tmp\test\1\y.doc
c:\tmp\test\2\y.doc

Hope this helps.

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

It means that you're trying to retrieve an element from the array that it does not contain. If the array is empty, it contains no elements, so any element you would try to retrieve will lead to that error. If you know it's empty, why are you trying to get something from it?

Compare it to opening your fridge, seeing it's empty, and still sticking your hand in there expecting to grab milk :) 

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

Well, the way to prevent the error is simple: don't try and access an element that does not exist. (Not trying to be pedantic - it's actually the solution :) )

You can tell how many elements an array contains by using UBound($myArray). You can tell whether a variable is an array in the first place by IsArray($myArray). So you have to write your script to be smart enough not to access an element that does not exist, and to not address a variable as an array if it's not an array.

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
Share on other sites

I asked a question earlier: "If you know it's empty, why are you trying to get something from it?" That was a serious question. If you know the array is empty, you also know that there's no element to retrieve, so if you try it anyway, you are doing it wrong.

You have to make your script check the array to see whether the element you need actually exist, or alternatively make it understand in which situations looking up the array makes no sense. A good example of this is when a function returns an array, except when there's an error. Like StringRegExp.

#include <Array.au3>

handleThis(go("[abc")) ; broken pattern - StringRegExp will return 0 (instead of an array) and will set @error
handleThis(go("(\w+)")) ; valid pattern - StringRegExp will return 5 matches
handleThis(go("thisWillNotBeFound")) ; valid pattern - StringRegExp will lead to 0 matches, i.e. an empty array

Func handleThis($aResult)
    If @error Then
        ; something went wrong, so let's not try and address the result as an array
        MsgBox(16, 0, "error")
    Else
        ; no error occured, so we can assume it's an array.
        MsgBox(64, 0, "The array contains " & UBound($aResult) & " elements.")
        _ArrayDisplay($aResult)
        ; If we would blindly assume the array has a third element, we would get an error when that assumption
        ; ... turns out false. So if we're interested in a third element BUT want to be safe against errors,
        ; ... we should first check whether that third element is actually available.
        If UBound($aResult) >= 3 Then ; (at least) 3 array elements exist, i.e. index 0, index 1 and index 2
            $thirdElement = $aResult[2]
            MsgBox(64, 0, "There is a third element: " & $aResult[2])
        EndIf
    EndIf
EndFunc   ;==>handleThis

Func go($pattern)
    Return StringRegExp("hello I am Sad Bunny", $pattern, $STR_REGEXPARRAYGLOBALMATCH)
EndFunc   ;==>go

Hope this helps.

Edited by SadBunny

Roses are FF0000, violets are 0000FF... All my base are belong to you.

Link to comment
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
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...