powered by simpleCommunicator - 2.0.59     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / WinForms, .Net Framework [игнор отключен] [закрыт для гостей] / Потокобезопасное использование потоконебезопасных коллекций
25 сообщений из 145, страница 3 из 6
Потокобезопасное использование потоконебезопасных коллекций
    #38758501
netivan
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79cdtyjvХахаха, так у вас еще и члены класса не волатильные. То есть вообще никаких гарантий в многопоточно окружении у вас нет. Вердикт - на помойку, СРОЧНО !

Критиковать каждый горазд, особенно старый код под .net2. Мы ждем вашего кода. С volatile в пределах заданного ТС коридора.

Кстати, товарищ эксперт, если мой код исправить так, вас это устроит?

Код: c#
1.
2.
3.
4.
5.
6.
if ( 0 != Thread.VolatileRead(queue.Count) ) {
    lock(queue) {
        if ( 0 != Thread.VolatileRead(queue.Count) )
            var msq = queue.Dequeue();
    }
}



Зачем нам смотреть в Java, когда есть ConcurrentQueue и его исходники? Чем он так плох?
он еще его не завизировал, вот чем плох он!
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758502
Фотография skyANA
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
netivanавторХахаха, так у вас еще и члены класса не волатильные. То есть вообще никаких гарантий в многопоточно окружении у вас нет. Вердикт - на помойку, СРОЧНО! напиши идеальный, оценимОн только по чужим исходникам на Java способен код на C# писать. И у него это плохо получается.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758516
mikron
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Где-то в степиmikron,
по первому, в код не вникал, но наверное проверка что не залез кто то из другого потока,

Вот я и спрашиваю, как эта "проверка" работает? что удержит оптимизатор от её полного удаления за ненужностю?
Оптимизатор может зделать и так.
Код: c#
1.
2.
3.
4.
5.
oldTail = _tail; 
if (_tail == oldTail) {
 oldTailNext = oldTail.Next; 
 ...
}


Тогда очевидно, что она безполезна.

Где-то в степипри беглом взгляде в сети данный код используется в около сотни проектах, наверное можно его считать верифицированным ( условно)

Вот она чудотворящая сила копипасты. Иммено так количество переходит в качество. Ещё одно подверждение марксистко ленинской диалектической теории :))
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758545
Фотография ЕвгенийВ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
mikron[src c#]
oldTail = _tail;
oldTailNext = oldTail.Next;
if (_tail == oldTail) // Optimisation can remove comparission

Откуда это?
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758549
Фотография ЕвгенийВ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вот , хороший пост Эрика.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758550
mikron
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ЕвгенийВmikron[src c#]
oldTail = _tail;
oldTailNext = oldTail.Next;
if (_tail == oldTail) // Optimisation can remove comparission

Откуда это?
16620467
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758597
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
netivanнапиши идеальный, оценимЗачем мне писать свой, если уже все написано? Причем написано эффективно и корректно, в отличие от вашей реализации?
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758603
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79Кстати, товарищ эксперт, если мой код исправить так, вас это устроит?

Код: c#
1.
2.
3.
4.
5.
6.
if ( 0 != Thread.VolatileRead(queue.Count) ) {
    lock(queue) {
        if ( 0 != Thread.VolatileRead(queue.Count) )
            var msq = queue.Dequeue();
    }
}

В вашем коде есть три ошибки:
1) Он не компилируется, так как в VolatileRead надо отдавать адрес переменной, а вы туда отдаете свойство, чего делать нальзя.
2) Нужен lock(queue) и в другом треде, который делает Enqueue(). Вы про это не упомянули, а значит и не подумали.
3) Если бы Thread.VolatileRead(queue.Count) все таки работал, то он не нужен был бы внутри lock(queue), хватило бы и обычного чтения.

Двойка вам.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758608
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
mikronГде-то в степиmikron,
по первому, в код не вникал, но наверное проверка что не залез кто то из другого потока,

Вот я и спрашиваю, как эта "проверка" работает? что удержит оптимизатор от её полного удаления за ненужностю?Да ничего. Поля не волатильны, оптимайзер волен делать, что захочет. Но вот Arm79 считает, что это казуистика, и такой код всегда работает, а модель памяти придумали ботаны-теоретики.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758624
codearticles.ru
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ЕвгенийВ Вот , хороший пост Эрика.
Бесполезное гонево ламера, причем 5-летней давности. Откровенный бред человека, который в самом начале признается в своей некомпетентности. Я бы не стал "козырять" такими позорными темами.

P.S. Возможно сейчас у этого веб евангелиста мнение поменялось.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758639
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
cdtyjvArm79Кстати, товарищ эксперт, если мой код исправить так, вас это устроит?

Код: c#
1.
2.
3.
4.
5.
6.
if ( 0 != Thread.VolatileRead(queue.Count) ) {
    lock(queue) {
        if ( 0 != Thread.VolatileRead(queue.Count) )
            var msq = queue.Dequeue();
    }
}


В вашем коде есть три ошибки:
1) Он не компилируется, так как в VolatileRead надо отдавать адрес переменной, а вы туда отдаете свойство, чего делать нальзя.
2) Нужен lock(queue) и в другом треде, который делает Enqueue(). Вы про это не упомянули, а значит и не подумали.
3) Если бы Thread.VolatileRead(queue.Count) все таки работал, то он не нужен был бы внутри lock(queue), хватило бы и обычного чтения.

Двойка вам.

Пичалька. Я действительно не проверял код, но касаемо 3 пункта вы неправы. Если lock объекта отнюдь не означает, что синхронизируются по всех процессорных кэшах значение всех его полей.

Пункт 2 - это лишь ваши фантазии, о чем я там думал.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758645
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79о касаемо 3 пункта вы неправы. Если lock объекта отнюдь не означает, что синхронизируются по всех процессорных кэшах значение всех его полей.Как раз таки означает. Если бы этого не было, то следующий код бы не работал, а он работает:
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
int x;
int y;
object mux= new object();

// Thread 1:
lock (mux)  
{
    x = 1;
    y = 1;
}

// Thread 2:
lock (mux) 
{
    if (x == 1)
        Debug.Assert(y == 1);
}


Все, я заканчиваю с вами диалог. Разберитесь сначала с моделью памяти, потом поговорим.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758647
Фотография ЕвгенийВ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
codearticles.ruЕвгенийВ Вот , хороший пост Эрика.
Бесполезное гонево ламера, причем 5-летней давности. Откровенный бред человека, который в самом начале признается в своей некомпетентности. Я бы не стал "козырять" такими позорными темами.

P.S. Возможно сейчас у этого веб евангелиста мнение поменялось.
МСУ, Гайдар в принципе на такие статьи не способен, это перевод блога Эрика Липперта , который не самый последний стековерфлоу и который много лет делал .NET и С#, всякие там деревья выражений, женерики и прочие контрвариантности и чем там ты еще там пользуешься, его рук дело.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758673
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79lock объекта отнюдь не означает, что синхронизируются по всех процессорных кэшах значение всех его полей
cdtyjvКак раз таки означает
Да, действительно, тут я дал маху.

cdtyjvНо вот Arm79 считает, что это казуистика, и такой код всегда работает
Но тут я по прежнему на своем стою - тот код, который я привел, рабочий. Тот, а не такой. Разница есть.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758684
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79Но тут я по прежнему на своем стою - тот код, который я привел, рабочий. Тот, а не такой. Разница есть.Да ради бога. Разнесут вас на очередном собеседовании за такой код - может быть начнете по-другому смотреть на вещи.
Код бывает либо корректный, либо нет. Ваш код некорректен, точно так же, как и код нашего коллеги, реализовавшего нерабочую конкурентную очередь. Никаких "конкретно мой" здесь нет.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758700
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
cdtyjvн

Еще раз:

1 итерация: Читающий поток смотрит на количество. Видит 0, не исполняется ничего
2 итерация: читающий поток видит количество 2 (хотя допустим, пишущие потоки закинули туда 10 объектов, и Count не синхронизирован). Входит lock, где Count уже засинхронизирован и там уже 10, то есть Count корректен. Обрабатывает эти 10 элементов.

Фактически ваша претензия сводится к тому, что объекты в очереди будут обработаны в разных итерациях, что при периодическом опросе несущественно.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758707
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79 ,
Вовсе нет. Моя претензия заключается в том, что если один поток положил элемент в очередь и изменил _count с 0 на 1, то второй поток может продолжать видеть 0 неограниченно долго .
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758709
codearticles.ru
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
ЕвгенийВМСУ, Гайдар в принципе на такие статьи не способен, это перевод блога Эрика Липперта

Да, я верю, что он тру кодер, но после таких слов

...За всю мою карьеру, необходимость написать код, который запускает второй рабочий поток, возникала, вероятно, менее полудюжины раз.

вникать в его поток воображения стало лень.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758732
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
codearticles.ru...За всю мою карьеру, необходимость написать код, который запускает второй рабочий поток, возникала, вероятно, менее полудюжины раз. вникать в его поток воображения стало лень.Все правильно он написал. Так как преимущественно используют тред-пулы.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758734
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
cdtyjv Arm79 ,
Вовсе нет. Моя претензия заключается в том, что если один поток положил элемент в очередь и изменил _count с 0 на 1, то второй поток может продолжать видеть 0 неограниченно долго .
Но ведь видит же? Может, потому, что при записи в эту очередь тоже lock и там обновляются значения Count?
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758741
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79Но ведь видит же? Может, потому, что при записи в эту очередь тоже lock и там обновляются значения Count?Нет гарантий, что чтение переменной вне лока увидит изменение, которое внес другой поток внутри лока. Что бы его увидеть нужен барьер памяти до чтения, которого в вашем случае нет.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758749
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
cdtyjvArm79Но ведь видит же? Может, потому, что при записи в эту очередь тоже lock и там обновляются значения Count?Нет гарантий, что чтение переменной вне лока увидит изменение, которое внес другой поток внутри лока. Что бы его увидеть нужен барьер памяти до чтения, которого в вашем случае нет.

Так это если разовое. Если речь о периодическом опросе, то проблем не будет, Count будет прекрасно меняться.
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758771
Arm79
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вот код, компилировал его в Release, запускал вне студии. Раз 10 запускал на 8ядерной машине, не разу не зависло. Обратите внимание, сначала запускал читающий поток, чтобы гарантированно первой итерацией не проскакивать в lock.

Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
class Program
    {
        static readonly Queue<string> _queue = new Queue<string>();

        static void Main(string[] args)
        {
            (new Thread(() =>
                {
                    while (true)
                    {
                        if (0 < _queue.Count)
                        {
                            lock (_queue)
                            {
                                while (0 != _queue.Count)
                                {
                                    string msg = _queue.Dequeue();
                                    Console.WriteLine(msg);
                                }
                            }
                        }                        
                    }

                }) {IsBackground = true}).Start();
            Thread.Sleep(1000);

            Enumerable.Range(1, 25).ToList().ForEach(i => (new Thread(Handler) {IsBackground = true}).Start(i));

            Console.ReadKey();
        }

        static void Handler(object state)
        {
            while (true)
            {
                lock (_queue)
                    _queue.Enqueue(((int)state).ToString());
                Thread.Sleep(1);
            }
            
        }
    }
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758792
codearticles.ru
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
cdtyjvВсе правильно он написал. Так как преимущественно используют тред-пулы.
Причем тут это?
...
Рейтинг: 0 / 0
Потокобезопасное использование потоконебезопасных коллекций
    #38758824
cdtyjv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Arm79 ,

Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
            Queue<int> queue = new Queue<int>();

            new Thread(() =>
            {
                Thread.Sleep(1000);

                lock (queue)
                {
                    queue.Enqueue(1);
                }

                Console.WriteLine(Thread.CurrentThread.ManagedThreadId + ": Added element to queue.");

            }).Start();

            Console.WriteLine(Thread.CurrentThread.ManagedThreadId + ": Waiting for size change...");

            while (true)
            {
                if (queue.Count > 0)
                {
                    Console.WriteLine(Thread.CurrentThread.ManagedThreadId + ": Noticed size change.");

                    break;
                }
            }



1) Скомплиировать в Release.
2) Запустить без дебагера.

Еще вопросы будут у вас?
...
Рейтинг: 0 / 0
25 сообщений из 145, страница 3 из 6
Форумы / WinForms, .Net Framework [игнор отключен] [закрыт для гостей] / Потокобезопасное использование потоконебезопасных коллекций
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]