Я пытаюсь повториться и узнать больше, усовершенствованное использование и опции при вырезании деревьев с подцепляют джунгли на вилку C. Но по-дурацки я нахожу пример, который должен быть очень легким, поскольку я работал с ветвлениями прежде и даже написал некоторый код, но я не могу понять это полностью.
Здесь прибывает:
main() {
if (fork() == 0) {
if (fork() == 0) {
printf("3");
}
else if ((wait(NULL)) > 0) {
printf("2");
}
}
else {
if (fork() == 0) {
printf("1");
exit(0);
}
if (fork() == 0) {
printf("4");
}
}
printf("0");
return 0;
}
Возможные решения:
где 2, 5 и 6 корректные ответы.
В первую очередь, не должен там быть четыре, обнуляет в выводе? Второй... Как каждый приходит к решению вообще? Выполнение этого на бумаге в течение почти часа и я даже не близко к пониманию, почему данное решение более корректно, чем ложные (за исключением nr3, поскольку это не может закончиться 2, так как 0 должен следовать).
Кто-либо с его ветвлениями под контролем, кто может предложить некоторое хорошее объяснение?
Править:
Найденный этим здесь смотрят на PDF с 2009. Люди могут теперь прекратить делать сообщения об этом являющемся домашней работой и на самом деле попытаться помочь? Если не найдите, что некоторые другие темы проводят Ваше время. Спасибо!
Я думаю, должно быть 4 нуля, и это то, что я увижу, запустив ваш код ...
Хороший способ проанализировать это - чтобы нарисовать диаграмму, подобную этой - я показал вилки как *
, где родительский элемент продолжается горизонтально, а дочерний элемент - ниже, так что каждый отдельный процесс находится в отдельной строке:
----*----*----*----0----exit (return from main)
| | |
| | +----4----0----exit (return from main)
| |
| +----1----exit (explicitly)
|
+-----*----wait----2----0----exit (return from main)
|
+----3----0----exit (return from main)
Теперь это просто чтобы увидеть, что из-за wait ()
вы должны увидеть 3
, за которым некоторое время спустя следует 0
, перед увидит ] 2
, за которым следует 0
.
Во-первых, вам нужно выбрать из , а не всех возможных перестановок вывода. Скорее, их всего несколько. Глядя на исходный код, мы можем заметить несколько вещей, которые исключают возможность:
exit (0)
, не продолжая печатать «0». . Таким образом, на выходе ожидается только три нуля. Также по этой причине последний символ должен быть 0 или 1. ждем (NULL)
дочернего элемента перед выводом «2». Это означает, что потомок, которого мы ждем, всегда будет печатать 3, а затем 0, прежде чем мы напечатаем 2. Это единственное, что можно сказать окончательно об этой проблеме. Это означает, что любой правильный ответ должен заканчиваться на 0 или 1 и должен иметь как 3, так и 0 перед 2. Этим критериям соответствуют только 2, 5 и 6.
{{1 }} В выводе только три нуля из-за оператора exit
после того, как программа напечатает 1. Этот оператор немедленно завершает процесс. Эд: Нет, на самом деле там должно быть 4 нуля; Я упустил из виду исходный процесс. Понятия не имею, почему в ответе нет четырех нулей.
В целом, анализируя ответы на вопрос, вы должны понимать следующее:
fork ()
, вы создаете новый процесс, и старый процесс также продолжается, оба из одной и той же точки fork
. Это будет 0 (ложь), если вы находитесь в новом процессе, и ненулевое (истина), если вы находитесь в старом процессе. wait (NULL)
приостанавливает выполнение текущего процесса до тех пор, пока один из процессов, ответивших из него, не завершится. Чтобы уточнить 4, представьте, что у вас есть два процесса, один из которых выводит «abc», а другой - «xyz». Возможны такие выходные данные, как «abxcyz», «xaybcz» или «xyabcz», поскольку последовательности abc и xyz появляются по порядку. Однако вывод «abzcxy» невозможен, потому что z не может стоять перед x, поскольку они оба исходят из одного процесса, а операторы, которые их выводят, появляются в другом порядке.
Они предполагают, что когда вы вызываете wait (NULL), будет выполнена вся вилка '3'. Это включает печать «0» в конце этой вилки. Таким образом, ответы 1 и 4 неверны, потому что в них нет «0» перед «2».
Насчет того, почему нет четырех нулей, я не знаю.