使用 fork (process) 而不是 pthread 来达到同样的效果
use fork (process) instead of pthread to acieve the same
我通过创建并行线程实现了以下代码的并发。但是,我应该如何使用 fork() 创建子进程并完成与下面的 main() 相同的工作?我想避免创建任何线程。
struct function_args
{
pthread_t thread;
char *command;
};
int main()
{
while (1)
{
if (mode == 1)
printf("$> ");
if ((nread = getline(&line, &linecap, in)) > 0)
{
char *command;
int commands_num = 0;
struct function_args args[BUFF_SIZE];
// remove newline character
if (line[nread - 1] == '\n')
line[nread - 1] = '[=10=]';
char *temp = line;
while ((command = strsep(&temp, "&")) != NULL)
if (command[0] != '[=10=]')
{
args[commands_num++].command = strdup(command);
if (commands_num >= BUFF_SIZE)
break;
}
for (size_t i = 0; i < commands_num; i++)
if (pthread_create(&args[i].thread, NULL, &parseInput, &args[i]) != 0)
printError();
for (size_t i = 0; i < commands_num; i++)
{
if (pthread_join(args[i].thread, NULL) != 0)
printError();
if (args[i].command != NULL)
free(args[i].command);
}
}
else if (feof(in) != 0)
{
atexit(clean);
exit(EXIT_SUCCESS); // EOF
}
}
return 0;
}
我知道 pid = fork()
returns 一个 processid,对于子进程为 0,对于父进程为 >0。但是,在下面我处理多个 argv
的 for 循环中,我不确定如何翻译我的 main() 来这样做。
这真的取决于你在做什么。一般而言,您可以执行以下操作:
for (size_t i = 0; i < commands_num; i++)
{
pid_t pid = fork();
if (pid == 0)
{
parseInput(&args[i]);
exit(0);
}
else if (pid == -1)
printError();
else
args[i].thread = pid;
}
children 进程独立于 parent 工作并继续完成它们的任务,因此可能不需要在此处执行与 pthread_join()
相同的操作,在这种情况下是 waitpid()
,除非 parent 过程必须等待他们的产品对其进行处理。
并且说到这一点,一旦进程被分叉,它们将不再共享相同的内存 space,因此在 children 和 parent 之间传输信息可能是一个挑战在自身。如果您只是将内容打印到 stdout
,那么您就可以开始了,否则您将不得不找出使 parent 和 children 通信的管道。
另一种使用系统本机线程(或特别是 pthreads)的替代方法是使用一些绿色线程库,例如 libdill,理论上即使在不支持的系统中它也会启用 multi-threading原生 multi-threading.
我通过创建并行线程实现了以下代码的并发。但是,我应该如何使用 fork() 创建子进程并完成与下面的 main() 相同的工作?我想避免创建任何线程。
struct function_args
{
pthread_t thread;
char *command;
};
int main()
{
while (1)
{
if (mode == 1)
printf("$> ");
if ((nread = getline(&line, &linecap, in)) > 0)
{
char *command;
int commands_num = 0;
struct function_args args[BUFF_SIZE];
// remove newline character
if (line[nread - 1] == '\n')
line[nread - 1] = '[=10=]';
char *temp = line;
while ((command = strsep(&temp, "&")) != NULL)
if (command[0] != '[=10=]')
{
args[commands_num++].command = strdup(command);
if (commands_num >= BUFF_SIZE)
break;
}
for (size_t i = 0; i < commands_num; i++)
if (pthread_create(&args[i].thread, NULL, &parseInput, &args[i]) != 0)
printError();
for (size_t i = 0; i < commands_num; i++)
{
if (pthread_join(args[i].thread, NULL) != 0)
printError();
if (args[i].command != NULL)
free(args[i].command);
}
}
else if (feof(in) != 0)
{
atexit(clean);
exit(EXIT_SUCCESS); // EOF
}
}
return 0;
}
我知道 pid = fork()
returns 一个 processid,对于子进程为 0,对于父进程为 >0。但是,在下面我处理多个 argv
的 for 循环中,我不确定如何翻译我的 main() 来这样做。
这真的取决于你在做什么。一般而言,您可以执行以下操作:
for (size_t i = 0; i < commands_num; i++)
{
pid_t pid = fork();
if (pid == 0)
{
parseInput(&args[i]);
exit(0);
}
else if (pid == -1)
printError();
else
args[i].thread = pid;
}
children 进程独立于 parent 工作并继续完成它们的任务,因此可能不需要在此处执行与 pthread_join()
相同的操作,在这种情况下是 waitpid()
,除非 parent 过程必须等待他们的产品对其进行处理。
并且说到这一点,一旦进程被分叉,它们将不再共享相同的内存 space,因此在 children 和 parent 之间传输信息可能是一个挑战在自身。如果您只是将内容打印到 stdout
,那么您就可以开始了,否则您将不得不找出使 parent 和 children 通信的管道。
另一种使用系统本机线程(或特别是 pthreads)的替代方法是使用一些绿色线程库,例如 libdill,理论上即使在不支持的系统中它也会启用 multi-threading原生 multi-threading.