[Tutor] threads
Danny Yoo
dyoo at hkn.eecs.berkeley.edu
Wed Feb 23 20:32:12 CET 2005
On Wed, 23 Feb 2005, Shitiz Bansal wrote:
> I am trying to build a traffic network simulator using python, for my
> degree project.
>
> I need to run at least 5-6000 cars simultaneously. I wanted to run each
> car in a separate thread. However , after about 400 threads i am unable
> to create new threads.
Hello!
Python is using your operating system's native thread implementation; it's
possible that you're running into a platform-specific issue.
>From looking at the error message:
> Traceback (most recent call last):
> File "<pyshell#24>", line 2, in -toplevel-
> i.start()
> error: can't start new thread
I see the error message "error: can't start new thread". I did a Google
search and found that Windows reports this error if we hit it with
thousands of threads at a time:
http://mail.python.org/pipermail/python-checkins/2003-July/036869.html
You may need to raise the thread limit on your operating system. That
being said, doing a simulation through threads might not be the easiest
thing to do.
Instead of representing each car as a thread, you may be able to make
things work by keeping all car in a priority queue, and do a kind of
discrete simulation without threads.
For example, here is a program that simulates people who say that they are
hungry:
######
import heapq
import random
"""Demo of heapq for doing discrete simulation."""
class Scheduler:
"""A scheduler keeps track what the current time is, and what
event should occur next."""
def __init__(self):
self.currentTime = 0
## self.queue will be a list of (scheduledTime, callable) tuples.
self.queue = []
def after(self, delay, event):
"""Adds a new event to the queue."""
timeAndEvent = (self.currentTime + delay, event)
heapq.heappush(self.queue, timeAndEvent)
def hasNext(self):
"""Returns true if there are still events to be processed."""
return len(self.queue) > 0
def next(self):
"""Returns the time and next event to be executed.
Precondition: we have more events."""
assert self.queue
if self.queue:
timeAndEvent = heapq.heappop(self.queue)
self.currentTime = timeAndEvent[0]
return timeAndEvent
class Person:
"""A person knows their name, and what scheduler they belong to."""
def __init__(self, name, sched):
self.name, self.sched = name, sched
def neutralState(self):
"""In a neutral state, a person can either eat or get hungry."""
print self.name, "is making a choice..."
nextState = random.choice([self.sleepingState,
self.hungryState])
self.sched.after(4, nextState)
def sleepingState(self):
"""A person will wake up in 12 minutes."""
print self.name, "snores..."
self.sched.after(12, self.wakeState)
def wakeState(self):
print self.name, "wakes up!"
self.sched.after(1, self.neutralState)
def hungryState(self):
print self.name, "is hungry. Food..."
self.sched.after(3, self.eatingState)
def eatingState(self):
print self.name, "is eating. Yum."
self.sched.after(10, self.neutralState)
if __name__ == '__main__':
scheduler = Scheduler()
sam = Person("sam", scheduler)
max = Person("max", scheduler)
## Let's start up the initial conditions: sam will be eating, and
## max will be sleeping.
scheduler.after(0, sam.eatingState)
scheduler.after(0, max.sleepingState)
for i in range(10):
time, event = scheduler.next()
print "time:", time
event()
######
This is a somewhat hacky program, but it's amusing to watch:
###
time: 0
sam is eating. Yum.
time: 0
max snores...
time: 10
sam is making a choice...
time: 12
max wakes up!
time: 13
max is making a choice...
time: 14
sam is hungry. Food...
time: 17
sam is eating. Yum.
time: 17
max snores...
time: 27
sam is making a choice...
time: 29
max wakes up!
###
It sounds like you want to hit the road with your car simulation; a
discrete simulation approach might be the most straightforward. If you
make each event discrete enough, it should work ok.
There are systems that support enormous amounts of concurrency; If you
really want to simulate each car with a thread, you may want to try
Stackless Python; it's a Python variant that supports the concept of
lightweight "tasklets".
http://www.stackless.com/
Also, you may want to also look at Erlang:
http://www.erlang.org/
Erlang is a programming language that's designed with concurrency in mind,
and I've heard that its concurrency support is second to none.
I hope this helps!
More information about the Tutor
mailing list