As the shell reads each line, it "handles" any special characters. This includes variable evaluation (variables start with a "$)," and filename expansion. Expansion of filenames occurs when the characters "*," "?," or "[" occur in a word. A question mark matches a single character. An asterisk matches any number of characters, including none. Square brackets are used to specify a range or particular combination of characters. Inside square brackets, a hyphen is used to specify a range or characters. Also, if the first character inside the square brackets is an exclamation point, the complement of the range is used. Let me give some examples:
Table 1
Examples of Bourne shell filename expansions
Pattern
Matches
*
Every file in the current directory
?
Files consisting of one character
??
Files consisting of two characters
??*
Files consisting of two or more characters
[abcdefg]
Files consisting of a single letter from a to g.
[gfedcba]
Same as above
[a-g]
Same as above
[a-cd-g]
Same as above
[a-zA-Z0-9]
Files that consist of a single letter or number
[!a-zA-Z0-9]
Files that consist of a single character not a letter or number
[a-zA-Z]*
Files that start with a letter
?[a-zA-Z]*
Files whose second character matches a letter.
*[0-9]
Files that end with a number
?[0-9]
Two character filename that end with a number
*.[0-9]
Files that end with a dot and a number
As you can see, the dot is not a special character. Filenames may or may not have a dot. UNIX Programers use the dot to standardize on the type of source code of each file, but that is just a convention. There is another convention, which concerns the shell:
正如你所看到的,dot不是特殊字符,文件名可有可無dot。unix程序員習慣使用dot來標准化源代碼的文件
Files whose name starts with a dot are not normally listed.
以dot開頭的文件不列出。
Again, it is a convention, but ls, find and the various shells follow this convention. This allows some files to be "secret," or perhaps invisible, by default.You must explicitly ask for these files, by including the dot as part of the filename. The pattern ".*" matches all hidden files.
我使用ls .* 效果:
/home/sumng/Documents/sh Documents下面有一個.secret文件。
ms@sumng-VirtualBox:~/Documents$ ls .*.secret
.:
file1 find sh test1 (2) test1zip test2.txt test3.txt
file1~ new3 test~ test1 (3) test1.zip test2.zip
file1.zip rm test1 test1.txt test2 test3
..:
Desktop examples.desktop Pictures suming.txt Videos
Documents hello.txt printf.sh Templates
Downloads Music Public Ubuntu One
可有看到除了把.secret顯示除了,也把Documents下其他文件顯示了,因為其他文件是在當前目錄,也是以dot開頭,也把上級目錄顯示
出來了。)
Remember that two hidden files are always in every directory, ".," which indicate the present directory, and "..," which indicates the directory above the current directory. If you want to match all hidden files except these two directories, there is no easy way to specify a pattern that will always match all files except the two directories. I use
.??
or
.[a-zA-Z]*
As I said, this does not match all combinations, but works most of the time. Hackers (or crackers, if you prefer) break into computers and often use strange filenames, like ". " or ".. " to hide their traces. You may not have noticed, but there was a space in these filenames. Refering to files with spaces in the names require quoting, which I will cover later. Personally, all of my hidden files are matched by ".[a-z]*" and all of my hidden directories are matched by ".[A-Z]*." This works because I made up my own convention, and always follow it.
The slash is also special, as it is used to indicate a directory path. Filename expansion does not expand to match a slash, because a slash can never be part of the filename. Also, the same rules for filename expansion of hidden files applies if the pattern follows a slash. If you want to match hidden files in a subdirectory, you must specify the explicit pattern. Table 2 lists some examples.
斜線也是特殊的,用來預示一個目錄,文件匹配不會匹配一個slash。因為slash永遠不是filename 的一部分。
Table 2
Filename Expansion with directories
Pattern
Matches
*
All non-invisible files
abc/*
All non-invisible files in directory abc
abc/.*
All invisible files in directory abc
*/*
All non-invisible files in all subdirectories below
*/.*
All invisible files in all subdirectories below
Filename expansions are based on the current directory, unless the filename starts with a slash.
The Bourne shell differs from the C shell if the meta-characters do not match any file. If this happens, the pattern is passed to the program unchanged. (The C shell will either do this, or generate an error, depending on a variable).
If you are not sure how something will expand, use the echo command to check. It generates output more compact than ls, and it will not list contents of directories like ls will. You will also notice the output is sorted alphabetically. The shell not only expans filenames, but sorts them, for all applications.