使用 argv 读取文件
Read a file using argv
目前代码正在读取文件并对记录进行排序,如下图,
#include"fileIO/file.h"
#define MAX_RECORD_SIZE 256 // Bad style
typedef struct{
int age;
char *lastName;
char *firstName;
}Person;
.....
int main(int argc, char *argv[]){
FILE *pFile = fopen("file.txt", "r");
....
callInsertionSort(getItemList(cache), getSize(getItemList(cache)), less);
}
其中,file.txt
是,
Age,LastName,FirstName
50,B,A
30,A,B
20,X,D
10,F,A
10,A,B
90,V,E
60,N,M
Execution:
$./sort.exe
Before sorting
Age,LastName,FirstName
50 B A
30 A B
20 X D
10 F A
10 A B
90 V E
60 N M
After sorting
Age,LastName,FirstName
10 F A
10 A B
20 X D
30 A B
50 B A
60 N M
90 V E
问题:
在不使用 fopen()
的情况下,有没有办法让 shell 将 file.txt
的内容作为命令行参数传递,文件中每行一个参数,(通过 argv
通过传递 shell 命令(sort.exe
)参数)?
您可以运行程序为:
IFS=$'\n'
./sort.exe $(cat file.txt)
文件的每一行都将成为程序的参数(将 IFS
设置为仅换行可防止文件中的空格成为参数分隔符)。
然后程序可以遍历 argv
(argv[0]
除外,其中包含程序名称)以对所有行进行排序。
请注意,参数的大小有限制,因此此方法的可扩展性不强。通常首选从文件中读取。
仅供参考,$(cat file.txt)
也可以写成 $(< file.txt)
如果 objective 将文件的每一行作为单独的命令行参数传递给 sort.exe
程序,那么您将需要 Bash(在标签中),您可以使用:
IFS=$'\n'; sort.exe $(cat file)
为了演示,采用替代命令 printf
和这样的数据文件,使用 ⧫
表示空白:
verbiage
spaced⧫out
⧫leading⧫and⧫trailing⧫
⧫⧫multiple⧫⧫spaces⧫⧫everywhere⧫⧫
运行 命令产生:
$ ( IFS=$'\n'; printf '[%s]\n' $(cat file) )
[verbiage]
[spaced out]
[ leading and trailing ]
[ multiple spaces everywhere ]
$
这使用外部 ( … )
到 运行 sub-shell 中的命令,这样我的交互 IFS
就不会搞砸了。在其他一些情况下它们是不必要的。
请注意,关于命令行参数(加上环境变量)的长度有一个 upper-bound - 有时多达 256 KiB,很少更大。这意味着您只能使用足够小的文件来执行此操作。在大多数情况下,您最好遵循 Unix (POSIX) sort
命令并直接从指定为 sort
命令参数的文件名中读取数据。
目前代码正在读取文件并对记录进行排序,如下图,
#include"fileIO/file.h"
#define MAX_RECORD_SIZE 256 // Bad style
typedef struct{
int age;
char *lastName;
char *firstName;
}Person;
.....
int main(int argc, char *argv[]){
FILE *pFile = fopen("file.txt", "r");
....
callInsertionSort(getItemList(cache), getSize(getItemList(cache)), less);
}
其中,file.txt
是,
Age,LastName,FirstName
50,B,A
30,A,B
20,X,D
10,F,A
10,A,B
90,V,E
60,N,M
Execution:
$./sort.exe Before sorting Age,LastName,FirstName 50 B A 30 A B 20 X D 10 F A 10 A B 90 V E 60 N M After sorting Age,LastName,FirstName 10 F A 10 A B 20 X D 30 A B 50 B A 60 N M 90 V E
问题:
在不使用 fopen()
的情况下,有没有办法让 shell 将 file.txt
的内容作为命令行参数传递,文件中每行一个参数,(通过 argv
通过传递 shell 命令(sort.exe
)参数)?
您可以运行程序为:
IFS=$'\n'
./sort.exe $(cat file.txt)
文件的每一行都将成为程序的参数(将 IFS
设置为仅换行可防止文件中的空格成为参数分隔符)。
然后程序可以遍历 argv
(argv[0]
除外,其中包含程序名称)以对所有行进行排序。
请注意,参数的大小有限制,因此此方法的可扩展性不强。通常首选从文件中读取。
仅供参考,$(cat file.txt)
也可以写成 $(< file.txt)
如果 objective 将文件的每一行作为单独的命令行参数传递给 sort.exe
程序,那么您将需要 Bash(在标签中),您可以使用:
IFS=$'\n'; sort.exe $(cat file)
为了演示,采用替代命令 printf
和这样的数据文件,使用 ⧫
表示空白:
verbiage
spaced⧫out
⧫leading⧫and⧫trailing⧫
⧫⧫multiple⧫⧫spaces⧫⧫everywhere⧫⧫
运行 命令产生:
$ ( IFS=$'\n'; printf '[%s]\n' $(cat file) )
[verbiage]
[spaced out]
[ leading and trailing ]
[ multiple spaces everywhere ]
$
这使用外部 ( … )
到 运行 sub-shell 中的命令,这样我的交互 IFS
就不会搞砸了。在其他一些情况下它们是不必要的。
请注意,关于命令行参数(加上环境变量)的长度有一个 upper-bound - 有时多达 256 KiB,很少更大。这意味着您只能使用足够小的文件来执行此操作。在大多数情况下,您最好遵循 Unix (POSIX) sort
命令并直接从指定为 sort
命令参数的文件名中读取数据。