Thread-local global variables?

Is it possible to define a variable whose value is global within a
particular each thread (including the main thread), yet distinct between
threads? For example, I've tried this:

$abc = 0

threads = []
2.times do |i|
  threads << Thread.new(i+1) do |i|
    $abc = i
    10.times do
      print "thread #{i}: abc = #{$abc}\n"
      sleep 0.5
    end
  end
end

10.times do
  print "thread 0: abc = #{$abc}\n"
  sleep 0.5
end

threads.each {|t| t.join}

Of course it prints:

thread 1: abc = 1
thread 2: abc = 2
thread 0: abc = 2
thread 1: abc = 2
thread 0: abc = 2
thread 2: abc = 2
thread 0: abc = 2
thread 2: abc = 2
thread 1: abc = 2
...

Is there any way to do this so that it prints like this?

thread 1: abc = 1
thread 2: abc = 2
thread 0: abc = 0
thread 1: abc = 1
thread 0: abc = 0
thread 2: abc = 2
thread 0: abc = 0
thread 2: abc = 2
thread 1: abc = 1
...

Thanks,
Earle

···

--
Posted via http://www.ruby-forum.com/.

Earle Clubb wrote:

Is it possible to define a variable whose value is global within a
particular each thread (including the main thread), yet distinct between
threads? For example, I've tried this:

the closest approximation is thread-locals:

thread = Thread.current
thread[:my_var] = "value"

(I've often thought it would be nice to have a syntax for per-thread globals, like $_x or something.)

···

--
       vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407

class Module
   def thattr name
     module_eval <<-code
       def #{ name }() Thread.current[#{ name.to_s.inspect }] end
       def #{ name }=(v) Thread.current[#{ name.to_s.inspect }] = v end
     code
   end
end

or similar is what i use

a @ http://codeforpeople.com/

···

On Jul 21, 2008, at 1:23 PM, Joel VanderWerf wrote:

he closest approximation is thread-locals:

thread = Thread.current
thread[:my_var] = "value"

(I've often thought it would be nice to have a syntax for per-thread globals, like $_x or something.)

--
we can deny everything, except that we have the possibility of being better. simply reflect on that.
h.h. the 14th dalai lama

class Module
   def thattr name
     module_eval <<-code
       def #{ name }() Thread.current[#{ name.to_s.inspect }] end
       def #{ name }=(v) Thread.current[#{ name.to_s.inspect }] = v end
     code
   end
end

class Foo
   thattr :x
end

foo = Foo.new
bar = Foo.new
foo.x = 1
p bar.x # ==> 1

This looks a little weird to me. But it does have the advantage that the method is defined only in the scope where you use it. (In a way, that's a disadvantage, too, since it obscures the fact that "x" really does have a bigger scope, namely the Thread.current#[] method.)

···

--
       vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407