9

I have some code which adds the word "_manual" onto the end of a load of filenames.. I need to change the script so that it deletes the last two letters of the filename (ES) and then replaces it with _ES_Manual for example: AC-5400ES.txt --> AC-5400_ES_manual.txt

How would i incorporate that function into this code?

folder = r"C:/Documents and Settings/DuffA/Bureaublad/test"
import os # glob is unnecessary
for root, dirs, filenames in os.walk(folder):
    for filename in filenames:
        fullpath = os.path.join(root, filename)
        filename_split = os.path.splitext(fullpath) # filename and extensionname (extension in [1])
        filename_zero, fileext = filename_split
        print fullpath, filename_zero + "_manual" + fileext
        os.rename(fullpath, filename_zero + "_manual" + fileext)
Alice Duff
  • 667
  • 6
  • 11
  • 18
  • what is the problem with the existing script ??? – rocksportrocker Aug 23 '11 at 12:19
  • i meant ES sorry! There is no problem with the script - but i need to incorperate replacing the ES currently in the filename into it! sorry if that is confusing! – Alice Duff Aug 23 '11 at 12:20
  • 1
    You should be able to get this on your own, so here is a hint. Use python's [slice notation](http://stackoverflow.com/questions/509211/good-primer-for-python-slice-notation). – Chris Pickett Aug 23 '11 at 12:20
  • 1
    @Alice Duff I find your present code heavy: you don't need to define objects **fullpath** and **filename_split** and **filename_zero** and **fileext**: it spoils the readability – eyquem Aug 23 '11 at 12:33
  • Sorry about the readability! Im too scared to delete anything incase it goes wrong.. – Alice Duff Aug 23 '11 at 12:38
  • @Alice Duff You must not test such a program on real directories. You must create a special directory in which you'll do all the tests in order to preserve all other directories from a severe problem. If you write ``os.rename(os.path.join(root, filename) , ....)`` in which **root** is this special directory or one of its subdirectories, you can't delete files elsewhere than in the special dir. If you remain so shy, you won't go very far in programming – eyquem Aug 23 '11 at 13:05
  • Ok thank you i will make sure to do that next time! Once i understand stuff a bit more i am sure i will become less shy with deleting stuff! – Alice Duff Aug 23 '11 at 13:17

5 Answers5

21

Try this:

import os
pathiter = (os.path.join(root, filename)
    for root, _, filenames in os.walk(folder)
    for filename in filenames
)
for path in pathiter:
    newname =  path.replace('ES.txt', '_ES_manual.txt')
    if newname != path:
        os.rename(path,newname)
hughdbrown
  • 47,733
  • 20
  • 85
  • 108
  • @Alice Duff _hughdbrown_'s code applies only for filenames ending with 'ES.txt' . It is correct if you want to change only these filenames. My code is more generic, it changes all filenames at their 2 last letters before extension. It may happen that it's not what you want, so you could upvote _hughdbrown_. But you can also consider to add a condition in my code to select filenames to change, hence my code is more general and adaptable. You have to consider and to choose. – eyquem Aug 23 '11 at 13:25
8

For a more generalized take on hughdbrown's answer. This code can be used to remove any particular character or set of characters.

import os

paths = (os.path.join(root, filename)
        for root, _, filenames in os.walk('C:\FolderName')
        for filename in filenames)

for path in paths:
    # the '#' in the example below will be replaced by the '-' in the filenames in the directory
    newname = path.replace('#', '-')
    if newname != path:
        os.rename(path, newname)
nicholas
  • 509
  • 1
  • 6
  • 12
  • Thanks @nicholas. Quick noobie question but what is paths = (...)? what is it doing? i understand is some kind of iteration command but I am still confused. What is it called and can you point me to something that explains it? – dodohjk Oct 06 '21 at 10:39
3

you could do:

for filename in filenames:
    print(filename) #should display AC-5400ES.txt
    filename = filename.replace("ES.txt","ES_manual.txt")
    print(filename) #should display AC-5400ES_manual.txt
    fullpath = os.path.join(root, filename)
    os.rename(fullpath, filename)
hughdbrown
  • 47,733
  • 20
  • 85
  • 108
JMax
  • 26,109
  • 12
  • 69
  • 88
  • But i need to keep the beginng part of the filename "AC-5400ES" - would this work for that? – Alice Duff Aug 23 '11 at 12:21
  • @Alice Duff: yes, this statement will take the filename string and replace every occurrence of "ES.txt" and replace it with "ES_manual.txt". This is the most basic way to handle what you described. If you need something more sophisticated, please tell us what you precisely want :) – JMax Aug 23 '11 at 12:29
  • hmm.. i tried this and everything just stays exactly the same! – Alice Duff Aug 23 '11 at 12:35
  • @Alice Duff: i edited my first answer to display my statement within your code. Do the statements `print` display the expected values? – JMax Aug 23 '11 at 12:40
  • You mean this: `filename = filename.replace("ES.txt","ES_manual.txt")` The version you offered has no side effects, as Alice's testing revealed. – hughdbrown Aug 23 '11 at 12:57
  • this just seems to print everything twice: the output was: ABC21ES.txt ABC21ES.txt – Alice Duff Aug 23 '11 at 13:04
  • @hughdbrown: thanks for the correction and +1 for your functional answer – JMax Aug 23 '11 at 19:23
3
for root, dirs, filenames in os.walk(folder):
    to_write = ['root == %s\n' % root]

    for filename in filenames:
        filename_zero, fileext = os.path.splitext(filename)
        newname = "%s_%s_manual%s" % (filename_zero[:-2],filename_zero[-2:],fileext)

        tu = (os.path.join(root, filename), os.path.join(root, newname))

        to_write.append('%s --> %s\n' % tu)
        os.rename(*tu)

    print '\n'.join(to_write)
eyquem
  • 26,771
  • 7
  • 38
  • 46
  • @Alice Duff It's charming the snake ! By the way, I use the object **to_write** to delay the print in chunks, so that general execution is faster – eyquem Aug 23 '11 at 13:21
0

Here is another alternative without using os.path.join or os.walk:

import os

fileLocation = "C:\\Documents and Settings\\DuffA\\Bureaublad\\test\\"
fileList = os.listdir(fileLocation)

for ii in fileList:
    newName = ii.replace('ES','_ES_Manual')
    if newName != ii:
        os.rename(fileLocation+ii,fileLocation+newName)