VassilSanych
|
Дата: 05.05.2013
Создание потока без пула - штука тяжёлая. Скорее всего это не lock путается, а то что приходит в него. PS Попробуйте Task.Run(...)
|
|
Спасибо:
|
|
|
|
|
casper-ss
|
Дата: 22.06.2013
А можно по подробнее про Task.Run...если не сложно...что это и с чем едят?первый раз увидел просто...
|
|
Спасибо:
|
|
|
|
|
yar1k0v
|
Дата: 23.06.2013
Task - задача для выполнения в фоновом потоке Код
new System.Threading.Tasks.Task(() => { }).Start();
или
new System.Threading.Tasks.TaskFactory().StartNew(() => { }).Start();
|
|
Спасибо:
|
|
|
|
|
yar1k0v
|
Дата: 23.06.2013
Цитата: private Thread t; private int i = 0; private readonly SyncObject _syncLock = new SyncObject(); private void button1_Click(object sender, RoutedEventArgs e) { i++; t = new Thread(SSS); t.Start(i); } private void SSS(object ii) { lock (_syncLock) { Debug.WriteLine("Отправка " + ii); Thread.Sleep(3000); Debug.WriteLine("Получение " + ii); } }
суть кода не понятна... вообще на переменную итерации в данном случае нужно накладывать лок, если вы тестили поочередность исполнения.
|
|
Спасибо:
|
|
|
|
|
MenDel
|
Дата: 23.06.2013
Может кому пригодится, Я использую такую конструкцию вместо лока, чтоб не путалась очередь команд посылающихся модему. Код
BlockingCollection<string[]> _queue = new BlockingCollection<string[]>(new ConcurrentQueue<string[]>());
Thread bt = new Thread(() =>
{
while (true)
{
// Thread.Sleep(1000); Можно добавить
if (_queue.Count == 0) continue;
var val = _queue.Take();
SmsSend(val); // Метод которому посылается val
}
}) { Name = "bt", IsBackground = true };
backThread.Start();
|
|
Спасибо:
|
|
|
|
|
MenDel
|
Дата: 23.06.2013
yar1k0v Цитата:Код
private Thread t;
private int i = 0;
private readonly SyncObject _syncLock = new SyncObject();
private void button1_Click(object sender, RoutedEventArgs e)
{
i++;
t = new Thread(SSS);
t.Start(i);
}
private void SSS(object ii)
{
lock (_syncLock)
{
Debug.WriteLine("Отправка " + ii);
Thread.Sleep(3000);
Debug.WriteLine("Получение " + ii);
}
}
суть кода не понятна... вообще на переменную итерации в данном случае нужно накладывать лок, если вы тестили поочередность исполнения. Суть кода в том что в основном потоке i итерируется, а в другом обрабатывается. В основном потоке лок на i нельзя накладывать.
|
|
Спасибо:
|
|
|
|
|
yar1k0v
|
Дата: 24.06.2013
Цитата:Суть кода в том что в основном потоке i итерируется, а в другом обрабатывается. В основном потоке лок на i нельзя накладывать. Вот пример: Код
int i = 0;
static object locker = new object();
public MainWindow()
{
InitializeComponent();
}
private void Start_Click(object sender, RoutedEventArgs e)
{
lock (locker) { i++; }
new System.Threading.Thread(() =>
{
lock (locker)
{
this.Dispatcher.BeginInvoke((Action)delegate()
{
Text.Text = "Started " + i.ToString();
});
System.Threading.Thread.Sleep(2000);
this.Dispatcher.BeginInvoke((Action)delegate()
{
Text.Text += Environment.NewLine;
Text.Text += "Finished " + i.ToString();
});
}
}).Start();
}
В данном примере ничего не путается. Почему lock на переменную итерации нельзя накладывать? Расскажите пожалуйста, буду знать. Спасибо!
|
|
Спасибо:
|
|
|
|
|
MenDel
|
Дата: 24.06.2013
|
|
|
|
yar1k0v Цитата:Суть кода в том что в основном потоке i итерируется, а в другом обрабатывается. В основном потоке лок на i нельзя накладывать. Вот пример: Код
int i = 0;
static object locker = new object();
public MainWindow()
{
InitializeComponent();
}
private void Start_Click(object sender, RoutedEventArgs e)
{
lock (locker) { i++; }
new System.Threading.Thread(() =>
{
lock (locker)
{
this.Dispatcher.BeginInvoke((Action)delegate()
{
Text.Text = "Started " + i.ToString();
});
System.Threading.Thread.Sleep(2000);
this.Dispatcher.BeginInvoke((Action)delegate()
{
Text.Text += Environment.NewLine;
Text.Text += "Finished " + i.ToString();
});
}
}).Start();
}
В данном примере ничего не путается. Почему lock на переменную итерации нельзя накладывать? Расскажите пожалуйста, буду знать. Спасибо! Если усыпить поток не на 2, а на 5 секунд вот, что получилось (я нажал на кнопку 15 раз) Результаты вывел не на форму, а в дебаг Код
Started 1
Поток '<Без имени>' (0x2bb4) завершился с кодом 0 (0x0).
Finished 2
Started 2
Поток '<Без имени>' (0x2a1c) завершился с кодом 0 (0x0).
Finished 3
Started 3
Поток '<Без имени>' (0x1830) завершился с кодом 0 (0x0).
Поток '<Без имени>' (0x1fe4) завершился с кодом 0 (0x0).
Finished 4
Started 4
Поток '<Без имени>' (0x14ac) завершился с кодом 0 (0x0).
Finished 5
Started 5
Поток '<Без имени>' (0x2934) завершился с кодом 0 (0x0).
Finished 5
1. В результате сработало только 5 раз из 15 2. Форма повисла 3. Не понял по какой причине в Finished число идет на 1 больше Есть еще мысли?
|
|
Спасибо:
|
|
|
|
|
yar1k0v
|
Дата: 24.06.2013
Прости, у меня такой проблемы не возникало. И сам пример, даже после нажатия 15 раз нормально работает. Может скажешь какова суть эксперимента? Возможно я смогу помочь по более конкретной задаче? Зависать может из за нехватки ресурсов, хз... Я не знаю как устроен метод Sleep(), я лишь знаю что он делает. Но видимо в нем причина зависания. Возможно пока он слипит текущий поток, запускается следующий. Ну и из за этого неполадки.
П.С.
Для меня например до сих пор загадка принцип работы new Random().Next(int min, int max) =) а именно почему при одновременном вызове нескольких таких методов, возвращаемые значения идентичны?
|
|
Спасибо:
|
|
|
|
|
MenDel
|
Дата: 25.06.2013
Про Random мне тоже интересно почему так.
Я использую модем для оповещения смсками и пытаюсь еще сделать так, чтоб когда инет отключается, мобильный инет автоматически подключался. Получается такая ситуация. Смс для модема поступают из разных мест и потоков, мне надо чтоб они ставились в очередь на отправку. Потому что на выполнение модемом команд нужно время.
|
|
Спасибо:
|
|
|
|