我有一个 C 程序,输入是通过命令行给出的。现在我想从文本文件传递输入。有两个输入,a
和b
,逐行编写如下:
a b
2 423
4 56.9
7 83.5
现在我想循环调用这个 txt 文件并逐行传递每个a
和值,以便为每个和值b
生成 C 程序的输出。a
b
为此,我想编写一个 shell 脚本,它将以读取模式调用 txt 文件,获取数据后,它将调用 C 程序,然后 C 程序将完成其余操作,包括输出。
由于我是这个 shell 脚本的新手,我对如何打开文本文件然后逐行读取数据并将它们存储在 shell 脚本中的某个变量中感到困惑。
请建议如何以读取模式打开文本文件,然后读取数据(可能并不总是整数)并将它们存储在其他变量中。
答案1
假设“输入通过命令行给出”意味着程序接受命令行参数,那么你应该能够做到这一点xargs
例如,给定一个最小的 C 程序
#include <stdio.h>
int main(int argc, char *argv[])
{
printf("Running %s\n", argv[0]);
for(int i=1; i<argc; i++) printf("arg %d = %s\n", i, argv[i]);
printf("\n");
}
使用 进行编译gcc -o someprog someprog.c
,以及一个由空格分隔的输入参数文件inputs.txt
$ cat inputs.txt
2 423
4 56.9
7 83.5
然后
$ xargs -L1 ./someprog < inputs.txt
Running ./someprog
arg 1 = 2
arg 2 = 423
Running ./someprog
arg 1 = 4
arg 2 = 56.9
Running ./someprog
arg 1 = 7
arg 2 = 83.5
如果您的输入文件有标题,则需要将其删除(tail
例如使用)。
如果并行处理对你的任务来说在计算上有利,那么你可以做类似的事情GNU 并行
parallel --colsep '[ \t]+' ./someprog {1} {2} :::: inputs.txt
答案2
以下是此类脚本的一个简单 Bash 示例:
#!/bin/bash
tail -n +2 "input-file" | sort -u | while read -a args
do
echo "${args[0]}" "${args[1]}"
done
第一个命令
tail -n +2 input-file
将输出文件的内容./input-file
,但没有第一行。这里假设 Bash 脚本和输入文件位于同一目录中 -./
是当前目录的路径。该输出将通过管道传输
|
到命令的标准输入sort
(-u
仅输出唯一的行),并将按第一列对该输入进行排序(用于man sort
找出更多选项)。命令的输出
sort -u
通过管道传输到循环的 STDINwhile-do-done
,其中每一行将作为read
一个数组-a
。此外,echo 命令将输出数组的第一个和第二个元素,名为
args
。您应该调整此行 -echo
使用 C 程序的路径和名称进行更改。
此示例的单行语法是:
tail -n +2 "./input-file" | sort -u | while read -a ar; do echo "${ar[0]}" "${ar[1]}"; done
另一个例子:
#!/bin/bash
INPUT_FILE="/path/to/input-file"
tail -n +2 "$INPUT_FILE" | sort -u | while read -a args
do
echo "${args[@]}"
done
- 这里文件的名称
input-file
随着变量的改变而改变$INPUT_FILE
,该变量的值是初步分配的。 - 还将同时
echo "${args[@]}"
输出数组的全部内容args
。