Есть три потока:
Имеется также диапазон от -100 до 100. Нужно, чтобы в результате работы всех трех потоков список содержал все эти числа в порядке возрастания. Все три потока опираются на один метод.
Код:
class Program
{
static object locker = new object();
static void Main(string[] args)
{
Thread thread1 = new Thread(Add);
Thread thread2 = new Thread(Add);
Thread thread3 = new Thread(Add);
thread1.Name = "thread1_odd";
thread2.Name = "thread2_even";
thread3.Name = "thread3_neg";
thread1.Start();
thread2.Start();
thread3.Start();
thread1.Join();
thread2.Join();
thread3.Join();
Node node = List.First;
while (node != null)
{
Console.WriteLine(node.Value);
node = node.Next;
}
}
static void Add()
{
for (int i = -100; i <= 100; i++)
{
lock (locker)
{
if (i >= 0 && i % 2 == 1 && Thread.CurrentThread.Name == "thread1_odd"
|| i >= 0 && i % 2 == 0 && Thread.CurrentThread.Name == "thread2_even"
|| i < 0 && Thread.CurrentThread.Name == "thread3_neg")
{
Thread.Sleep(10);
List.Add(i);
}
}
}
}
}
На всякий случай, List
- двусвязный список, который я реализовал самостоятельно.
Сначала должны добавляться в список отрицательные числа, потом по очереди четные-нечетные. Если оставить только положительные числа, то lock
здесь справляется: выводит числа от 1 до 100 по порядку, - но в данном случае нужно учесть отрицательные числа и 0, а это значит, нужно блокировать первые два потока, пока работает третий, до тех пор, пока отрицательные числа не закончатся. Ну и с нулем что-то сделать, думаю, запустить сначала второй поток, потом первый. Но как это сделать в одном методе?
Вам нужен не один лок, вам нужно два семафора, которые автоматически закрываются после того, как дождались их сигнала (AutoResetEvent
): один для четных и один для нечетных чисел. Они позволят вам чередовать вывод четных и нечетных чисел. Алгоритм получится следующим:
thread3_neg
выводит данные просто так. Когда доходит до -1, открывает четный семафор (т.к. согласно вашей проверке 0 -- четное число).thread1_odd
выводит данные только когда четный семафор открыт. После вывода он открывает нечетный семафор и останавливается на снова закрытом четном семафоре.thread2_even
выводит данные только когда нечетный семафор открыт. После вывода он открывает четный семафор и останавливается на снова закрытом нечетном семафоре.Но вообще, если вы не делаете эту задачу для разминки ума, я бы посоветовал прислушаться к комментарию @Bulson: свалить вывод всех трех потоков в одну кучу, отсортировать и вывести. Не забудьте синхронизировать добавление в коллекцию или использовать потокобезопасную коллекцию.
Оборудование для ресторана: новинки профессиональной кухонной техники
Частный дом престарелых в Киеве: комфорт, забота и профессиональный уход
Здравствуйте! Большую часть времени я пишу на С#, но мне всегда не хватало в этом прекрасном языке макросов (однажды попробовав макросы LISP, трудно...
При передаче большого объема данных в WCF службу, передаваемое приложение начинает безмерно потреблять ОЗУ 240>364>478>797 Мб и тд
Я хочу запускать скрипт, когда мой объект в юнити, допустим, преодолеет 47f по координате "y" в 2д пространстве
Сразу начну с сути проблемы, я хочу отправить на устройство echo пакет и при создании пакета размером больше, чем 255, выдает ошибку