Ruby multithread

Hi,
I am trying to use multithreading with multi acces webpage/database
but the problem is every thread is waiting for the other to finish t o
begin his work so I don't take advantage for the wait for a wabpage to
be downloaded for example
I read on internet that multithread in ruby is not the normal thread
like other langages, Is that true or I can find somethign to work it?
regards

···

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

I am trying to use multithreading with multi acces webpage/database
but the problem is every thread is waiting for the other to finish t o
begin his work so I don't take advantage for the wait for a wabpage to
be downloaded for example

Well, then maybe you have an issue in your application design. Can
you show the code?

I read on internet that multithread in ruby is not the normal thread
like other langages, Is that true or I can find somethign to work it?
regards

Whether Ruby uses green threads or OS threads depends on the Runtime.
However, if you do a lot IO then usually it does not matter that much.

Kind regards

robert

···

On Sat, Dec 17, 2011 at 2:57 PM, rubix Rubix <aggouni2002@yahoo.fr> wrote:

--
remember.guy do |as, often| as.you_can - without end
http://blog.rubybestpractices.com/

rubix Rubix wrote in post #1037123:

I am trying to use multithreading with multi acces webpage/database
but the problem is every thread is waiting for the other to finish t o
begin his work so I don't take advantage for the wait for a wabpage to
be downloaded for example
I read on internet that multithread in ruby is not the normal thread
like other langages, Is that true or I can find somethign to work it?

*If* you are using a library of C extensions, and your platform is MRI
(i.e. the standard ruby 1.8 or 1.9), you may find that when something
blocks in the C extension then it blocks the whole interpreter.

Sometimes, using a 'pure ruby' version of the library will perform
better under those circumstances (e.g. there's a pure ruby version of
the mysql API, as well as the C wrapper one)

But since you haven't posted any code or given any details of your
platform or what you're trying to talk to, I can't really be more
specific.

Regards,

Brian.

···

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

Hi,

Thank you for your answer and sorry for the late,
I have a queue of url:

···

---------------------------------------
Links =Queue.new
Links.push(url1)
Links.push(url2)
Links.push(url3)

# a method to download page
def openurl(uri)
object_uri = open(url)
end
def ParseHtml(url)
Extract Meta
end

def CommitPage(page)
insert meta to database (Mysql)
end

def Work(url)
openurl(url)
ParseHtml(url)
CommitPage(page)
end

t1=Thread.new{work(url1)}
t2=Thread.new{work(url2)}
t3=Thread.new{work(url3)}
t1.join
t2.join
t3.join
------------------------------------------
The cpu is idle when executing methods openurl, commitpage because they
take time accessing data but I notice that when executing this script
t2 will wait for t1 until it finishes and t3 for t2

have you a solution for this problem, because I am waisting a big time
like this

best regards

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

Thx,
what I am saying is that, ruby does not implement real thread, it means
that if a thread is waiting for a response of a distant server, ruby
can't use an other thread to some other work which is a wait of time
I will see if I can use JRuby for that
regards,

···

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

This pattern should work, although it's a bit ugly:

t1=Thread.new{work(url1)}
t2=Thread.new{work(url2)}
t3=Thread.new{work(url3)}
t1.join
t2.join
t3.join

A better approach would be:

threads = [url1, url2, url3].map { |url| Thread.new { work(url) } }

# joins each thread and obtains the value returned from the block you
passed to Thread.new
results = threads.map(&:value)

however keep in mind that the standard Ruby interpreter has a Global
Interpreter Lock (GIL), which means only one thread can run Ruby code at a
given time (however certain things like IO can be performed outside the GIL)

If you'd like to use Ruby without a GIL, take a look at JRuby or Rubinius
2.0

···

On Tue, Dec 20, 2011 at 1:31 PM, rubix Rubix <aggouni2002@yahoo.fr> wrote:

Hi,

Thank you for your answer and sorry for the late,
I have a queue of url:
---------------------------------------
Links =Queue.new
Links.push(url1)
Links.push(url2)
Links.push(url3)

# a method to download page
def openurl(uri)
object_uri = open(url)
end
def ParseHtml(url)
Extract Meta
end

def CommitPage(page)
insert meta to database (Mysql)
end

def Work(url)
openurl(url)
ParseHtml(url)
CommitPage(page)
end

t1=Thread.new{work(url1)}
t2=Thread.new{work(url2)}
t3=Thread.new{work(url3)}
t1.join
t2.join
t3.join
------------------------------------------
The cpu is idle when executing methods openurl, commitpage because they
take time accessing data but I notice that when executing this script
t2 will wait for t1 until it finishes and t3 for t2

have you a solution for this problem, because I am waisting a big time
like this

best regards

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

--
Tony Arcieri

This is just plain wrong - even in MRI and even in 1.8. Please read
again what people responded.

Cheers

robert

···

On Wed, Dec 21, 2011 at 1:01 PM, rubix Rubix <aggouni2002@yahoo.fr> wrote:

what I am saying is that, ruby does not implement real thread, it means
that if a thread is waiting for a response of a distant server, ruby
can't use an other thread to some other work which is a wait of time

--
remember.guy do |as, often| as.you_can - without end
http://blog.rubybestpractices.com/

This pattern should work, although it's a bit ugly:

t1=Thread.new{work(url1)}
t2=Thread.new{work(url2)}
t3=Thread.new{work(url3)}
t1.join
t2.join
t3.join

A better approach would be:

threads = [url1, url2, url3].map { |url| Thread.new { work(url) } }

This is unsafe, because you reuse "url": because of the scoping rules
a thread might see another thread's value. Better do this:

threads = [url1, url2, url3].map { |url| Thread.new(url) {|u| work(u) } }

# joins each thread and obtains the value returned from the block you
passed to Thread.new
results = threads.map(&:value)

Yep, Thread#value is vastly useful although rarely used.

Kind regards

robert

···

On Wed, Dec 21, 2011 at 12:00 AM, Tony Arcieri <tony.arcieri@gmail.com> wrote:

--
remember.guy do |as, often| as.you_can - without end
http://blog.rubybestpractices.com/