Szukaj…


Podstawowa semantyka wątków

Nowy wątek, niezależny od wykonywania głównego wątku, można utworzyć za pomocą Thread.new .

thr = Thread.new {
  sleep 1 # 1 second sleep of sub thread
  puts "Whats the big deal"
}

Spowoduje to automatyczne rozpoczęcie wykonywania nowego wątku.

Aby zatrzymać wykonywanie głównego wątku, dopóki nowy wątek się nie zatrzyma, użyj polecenia join :

thr.join #=> ... "Whats the big deal"

Zwróć uwagę, że wątek mógł już zostać zakończony po wywołaniu funkcji join, w takim przypadku wykonanie będzie kontynuowane normalnie. Jeśli wątek podrzędny nigdy nie zostanie przyłączony, a wątek główny zostanie ukończony, wątek podrzędny nie wykona żadnego pozostałego kodu.

Dostęp do udostępnionych zasobów

Użyj muteksu, aby zsynchronizować dostęp do zmiennej dostępnej z wielu wątków:

counter = 0
counter_mutex = Mutex.new

# Start three parallel threads and increment counter
3.times.map do |index|
  Thread.new do
    counter_mutex.synchronize { counter += 1 }
  end
end.each(&:join) # Wait for all threads to finish before killing the process

W przeciwnym razie wartość counter widocznego obecnie dla jednego wątku może zostać zmieniona przez inny wątek.

Przykład bez Mutex (patrz np. Thread 0 , gdzie Before i After różnią się o więcej niż 1 ):

2.2.0 :224 > counter = 0; 3.times.map { |i| Thread.new { puts "[Thread #{i}] Before: #{counter}"; counter += 1; puts "[Thread #{i}] After: #{counter}"; } }.each(&:join)
[Thread 2] Before: 0
[Thread 0] Before: 0
[Thread 0] After: 2
[Thread 1] Before: 0
[Thread 1] After: 3
[Thread 2] After: 1

Przykład z Mutex :

2.2.0 :226 > mutex = Mutex.new; counter = 0; 3.times.map { |i| Thread.new { mutex.synchronize { puts "[Thread #{i}] Before: #{counter}"; counter += 1; puts "[Thread #{i}] After: #{counter}"; } } }.each(&:join)
[Thread 2] Before: 0
[Thread 2] After: 1
[Thread 1] Before: 1
[Thread 1] After: 2
[Thread 0] Before: 2
[Thread 0] After: 3

Jak zabić wątek

Thread.kill use Thread.kill lub Thread.terminate :

thr = Thread.new { ... }
Thread.kill(thr)

Zakończenie wątku

Wątek kończy się, jeśli osiągnie koniec swojego bloku kodu. Najlepszym sposobem wcześniejszego zakończenia wątku jest przekonanie go, aby osiągnął koniec bloku kodu. W ten sposób wątek może uruchomić kod czyszczenia przed śmiercią.

Wątek uruchamia pętlę, podczas gdy zmienna instancji ciąg dalszy jest prawdziwa. Ustaw tę zmienną na false, a nić umrze śmiercią naturalną:

require 'thread'

class CounterThread < Thread
  def initialize
    @count = 0
    @continue = true

    super do
      @count += 1 while @continue
      puts "I counted up to #{@count} before I was cruelly stopped."
    end
  end

  def stop
    @continue = false
  end
end

counter = CounterThread.new
sleep 2
counter.stop


Modified text is an extract of the original Stack Overflow Documentation
Licencjonowany na podstawie CC BY-SA 3.0
Nie związany z Stack Overflow