From: ko1@... Date: 2017-01-31T08:32:18+00:00 Subject: [ruby-dev:49969] [Ruby trunk Feature#6694] Thread.new without block. Issue #6694 has been updated by Koichi Sasada. Existing Ideas: * (1) allow keywords for `new()` (like `new(name: "worker-thread")`) ** (1-1) introducing it immediately and break compatibility ** (1-2) introducing it and introduce proper keyword semantics (I doubt we can close this discussion) * (2) create threads by `new()` without block * (2-1) provide `proc:` keyword [Feature #6694] * (2-2) suspend thread and configure it before running https://bugs.ruby-lang.org/issues/3187#note-10 ** (3) Make builders (templates) with specific parameters https://bugs.ruby-lang.org/issues/3187#note-8 Simple one is (1-1), but it can introduce compatibility issue. Of course, I'm not sure how affect this incompatibility, but `csearch Thread.new\\\( | grep 'name:'` doesn't match on all of gems. (`name:` is only one property so it is not right example) ---------------------------------------- Feature #6694: Thread.new without block. https://bugs.ruby-lang.org/issues/6694#change-62757 * Author: Koichi Sasada * Status: Assigned * Priority: Normal * Assignee: Koichi Sasada * Target version: next minor ---------------------------------------- # Abstract Support Thread.new() without block. Before: `Thread.new(params...){|thread_local_params| ...}` After: `Thread.new(proc: lambda{|tl_params...| ...}, args: params..., other_thread_config...)` # Background Thread.new creates new Thread object and run passed block in another thread immediately. Thread.new can receive parameters and pass all parameters to block. ``` Thread.new(a, b, c) do |ta, tb, tc| # ta, tb, tc is thread local } ``` There are some request to specify thread configurations such as stack size described in [Ruby 1.9 - Feature #3187] (in this case, stack size for Fiber.new). However, we have no way to pass such thread configuration on the Thread.new(). # Proposal Allow Thread.new() without block. A block will be passed with proc parameter. Passed arguments will be passed with args parameter. ``` # ex1 Thread.new(){...} #=> Thread.new(proc: -> {...}) # ex2 Thread.new(a, b, c){|ta, tb, tc| ...} #=> Thread.new(proc: ->(ta, tb, tc){ ... }, params: [a, b, c]) ``` If you want to specify stack size, then: Thread.new(stack_size: 4096, proc: proc{...}, args: [a, b, c]) Note that I'll make another ticket for thread (and fiber) creation parameters. This change can be described with the following pseudo code: ``` def Thread.new(*args, &block) if block Thread.new_orig(*args, &block) else config = args[0] || raise ArgumentError stack_size = config[:stack_size] # ... and process another parameters Thread.new_orig(*config[:args], &config[:proc]) end end ``` # Another proposal On the [ruby-core:43385], Nahi-san proposed that if no block given on Thread.new(), then create "waiting" thread. Thread#run kicks waiting thread with parameters. ``` th = Thread.new(thread_config_params) ... th.run(params){|thread_local_params| ... } ``` We can combine with `proc:` parameter and this proposal. If `Thread.new()` doesn't have block and `proc:` parameter, then making a waiting thread. NOTE: Because we have already Thread#run, Thread#start is better than Thread#run? # Note I don't make any survey on other languages. Please give us your comments. -- https://bugs.ruby-lang.org/