0

What is the best way to replace all consecutive characters such as _+-."'? from a directory and all sub directory's names using GNU bash, version 4.3, using tools awk, sed, Perl rename or find?

AS suggested by @Ralf to rephrase:

The example would be to rename directories from

inital_situation . ├── dir1---FooFoo---xFoo.FOO │   └── file1---FooFoo---xFoo.FOO.mp4 ├── dir2+++FooFOO___xFoo.FOO │   └── file2___FooFOO___xFoo.FOO.mp4 ├── dir3...FooFOO...xFoo...FOO │   └── file3...FooFOO...xFoo...FOO.mp4 ├── dir4._-FOO._-xFoo._-FOO │   └── file4._-FOO._-xFoo._-FOO.mp4 ├── dir5+++FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_xFoo │   └── file5_-_FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_xFoo.mp4 ├── file1---FooFoo---xFoo.FOO.mp4 ├── file2+++FooFOO___xFoo.FOO.mp4 ├── file3...FooFOO...xFoo...FOO.mp4 ├── file4._-FOO._-xFoo._-FOO.mp4 ├── file5+++FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_FOO_-_xFoo.mp4 ├── xFoo_-[xFoo]_-[dir6] │   └── xFoo_-[xFoo]-file6.mp4 └── xFoo_-[xFoo]-file6.mp4

to

expected_results . ├── dir1-FooFoo-xFoo-FOO │   └── file1-FooFoo-xFoo-FOO.mp4 ├── dir2-FooFOO-xFoo-FOO │   └── file2-FooFOO-xFoo-FOO.mp4 ├── dir3-FooFOO-xFoo-FOO │   └── file3-FooFOO-xFoo-FOO.mp4 ├── dir4-FOO-xFoo-FOO │   └── file4-FOO-xFoo-FOO.mp4 ├── dir5-FOO-FOO-FOO-FOO-FOO-FOO-xFoo │   └── file5-FOO-FOO-FOO-FOO-FOO-FOO-xFoo.mp4 ├── file1-FooFoo-xFoo-FOO.mp4 ├── file2-FooFOO-xFoo-FOO.mp4 ├── file3-FooFOO-xFoo-FOO.mp4 ├── file4-FOO-xFoo-FOO.mp4 ├── file5-FOO-FOO-FOO-FOO-FOO-FOO-xFoo.mp4 ├── xFoo-xFoo-dir6 │   └── xFoo-xFoo-file6.mp4 └── xFoo-xFoo-file6.mp4

The following 2 examples from this post works well for renaming directories, sub directories and files.

find -name "* *" -type d | rename 's/ /_/g'    # do the directories first
find -name "* *" -type f | rename 's/ /_/g'

This is able to handle multiple layers of files and directories in a single bound

find . -depth -name "* *" -execdir rename 's/_/-/g' "{}" \; 

I have attempted several versions to replace or remove certain characters.

Replace dots and replace underscores

for f in *; do fn=`echo $f | sed 's/\(.*\)\.\([^.]*\)$/\1\n\2/;s/\./-/g;s/\n/./g'`; mv $f $fn; done

The following will remove brackets and parenthesis

rename 's/\[//g' * ; rename 's/\]//g' *
rename 's/\(//g' * ; rename 's/\)//g' *
  • 2
    What should happen to foo-.-?bar?++-baz."? – danzel Jan 18 '19 at 22:41
  • foo-.-?bar?++-baz." should become foo-bar-baz – Off Grid Jan 19 '19 at 1:56
1

Initial situation:

$ find .
.
./foo---foo...foo
./foo---foo...foo/foo...foo...foo
./foo---foo...foo/foo...foo...foo/file..name...name.extension
./foo---foo...foo/foo-+-+-+-+-+X
./foo---foo...foo/foo-+-+-+-+-+X/07. Testing.mov
./foo---foo...foo/foo------------foo
./foo---foo...foo/foo------------foo/01. Introduction.mov

Now execute:

$ find . -depth -execdir rename -E 's%^./%%' -E "s/[-_\.+\"'\?]{2,}/-/g" {} \;
./07. Testing.mov not renamed: 07. Testing.mov already exists
./01. Introduction.mov not renamed: 01. Introduction.mov already exists
./. not renamed: . already exists

Result:

$ find .
.
./foo-foo-foo
./foo-foo-foo/foo-foo-foo
./foo-foo-foo/foo-foo-foo/file-name-name.extension
./foo-foo-foo/foo-foo
./foo-foo-foo/foo-foo/01. Introduction.mov
./foo-foo-foo/foo-X
./foo-foo-foo/foo-X/07. Testing.mov

Your question should really contain examples like I added with "Initial situation:" and "Result:". Only that way anyone is able to understand what you want. Without it, it is just guessing game.

  • I attempted find . -depth -name "* *" -execdir rename -n "s/[-_+\.'\"\?]+/-/g" {} \; my results without renaming leaving the -n. /01. Introduction.mov renamed as -/01- Introduction-mov this renames the file extension to a hypen – Off Grid Jan 18 '19 at 21:33
  • And it also changes the leading ./ to -/. Not good. Do you really want to replace the . (dot) with a hyphen (as in the question)? – Ralf Jan 18 '19 at 21:57
  • I am only attempting to change consecutive characters such as _+-."'? from a directory. The dot for the file extension should remain. If the folder name contains a special characters such as _+-."'? that should be replaced with the hypen – Off Grid Jan 19 '19 at 1:54
  • 1
    @OffGrid you keep emphasizing "consecutive characters" yet your example appears to show FOO.foo changing a single character to become FOO-foo. Also what exactly do you mean by "the dot for the file extension" in the context of a directory name? – steeldriver Jan 19 '19 at 2:23
  • 1
    @OffGrid See update – Ralf Jan 19 '19 at 6:55

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.