MST

星途 面试题库

面试题:Ruby 中线程与并发编程的基础概念

请简要阐述 Ruby 线程的基本原理,以及在多线程编程中如何避免常见的资源竞争问题?
21.7万 热度难度
编程语言Ruby

知识考点

AI 面试

面试题答案

一键面试

Ruby 线程基本原理

  1. 轻量级执行单元:Ruby 线程是一种轻量级的执行单元,允许在同一进程内并发执行多个任务。它们共享进程的内存空间,包括全局变量和堆内存等。
  2. 协作式调度:Ruby 使用协作式调度(Cooperative Scheduling),也称为用户级线程调度。这意味着线程不会被操作系统抢占式地调度,而是在执行过程中主动让出 CPU 控制权,例如通过调用 Thread.pass 方法或执行一些 I/O 操作(如文件读取、网络请求)时,会暂停当前线程,允许其他线程运行。

避免多线程资源竞争问题的方法

  1. 互斥锁(Mutex)
    • 原理:互斥锁是一种简单的同步机制,它只允许一个线程在同一时间进入临界区(共享资源访问代码段)。
    • 使用示例
mutex = Mutex.new
shared_resource = 0

thread1 = Thread.new do
  mutex.lock
  shared_resource += 1
  mutex.unlock
end

thread2 = Thread.new do
  mutex.lock
  shared_resource += 1
  mutex.unlock
end

thread1.join
thread2.join
puts shared_resource # 输出 2,避免了资源竞争导致的错误结果
  1. 读写锁(ReadWriteLock)
    • 原理:读写锁允许同时有多个线程进行读操作,但只允许一个线程进行写操作。读操作之间不会产生资源竞争,因此可以并发执行,提高效率。
    • 使用示例
require 'thread'
rw_lock = ReadWriteLock.new
shared_data = []

reader1 = Thread.new do
  rw_lock.synchronize(:read) do
    # 读取 shared_data
  end
end

writer1 = Thread.new do
  rw_lock.synchronize(:write) do
    # 修改 shared_data
  end
end

reader1.join
writer1.join
  1. 条件变量(ConditionVariable)
    • 原理:条件变量用于线程间的同步通信,它允许线程在满足某个条件时被唤醒。通常与互斥锁一起使用,线程在等待条件变量时会释放持有的互斥锁,避免死锁。
    • 使用示例
mutex = Mutex.new
cv = ConditionVariable.new
ready = false

producer = Thread.new do
  mutex.lock
  # 生产数据
  ready = true
  cv.signal
  mutex.unlock
end

consumer = Thread.new do
  mutex.lock
  cv.wait(mutex) until ready
  # 消费数据
  mutex.unlock
end

producer.join
consumer.join
  1. 线程局部存储(Thread Local Storage)
    • 原理:每个线程都有自己独立的存储空间,不同线程之间不会共享这些数据,从而避免了资源竞争。
    • 使用示例
thread_local_var = Thread.current.thread_variable_get(:my_var) rescue nil
if thread_local_var.nil?
  thread_local_var = []
  Thread.current.thread_variable_set(:my_var, thread_local_var)
end
# 每个线程独立操作自己的 thread_local_var,无资源竞争问题