bpo-32208: update threading.Semaphore docs and add unit test (#4709)
* fix issue32208: update threading.Semaphore docs and add unit test to validate correct behavior * add test for blocking * Update threading.rst * semaphore: remove documentation validation tests and move 'return value' test to BaseSemaphore
This commit is contained in:
parent
961dbe0548
commit
a0374dd34a
|
@ -684,8 +684,8 @@ Semaphores also support the :ref:`context management protocol <with-locks>`.
|
|||
|
||||
.. class:: Semaphore(value=1)
|
||||
|
||||
This class implements semaphore objects. A semaphore manages a counter
|
||||
representing the number of :meth:`release` calls minus the number of
|
||||
This class implements semaphore objects. A semaphore manages an atomic
|
||||
counter representing the number of :meth:`release` calls minus the number of
|
||||
:meth:`acquire` calls, plus an initial value. The :meth:`acquire` method
|
||||
blocks if necessary until it can return without making the counter negative.
|
||||
If not given, *value* defaults to 1.
|
||||
|
@ -701,19 +701,19 @@ Semaphores also support the :ref:`context management protocol <with-locks>`.
|
|||
|
||||
Acquire a semaphore.
|
||||
|
||||
When invoked without arguments: if the internal counter is larger than
|
||||
zero on entry, decrement it by one and return immediately. If it is zero
|
||||
on entry, block, waiting until some other thread has called
|
||||
:meth:`~Semaphore.release` to make it larger than zero. This is done
|
||||
with proper interlocking so that if multiple :meth:`acquire` calls are
|
||||
blocked, :meth:`~Semaphore.release` will wake exactly one of them up.
|
||||
The implementation may pick one at random, so the order in which
|
||||
blocked threads are awakened should not be relied on. Returns
|
||||
true (or blocks indefinitely).
|
||||
When invoked without arguments:
|
||||
|
||||
* If the internal counter is larger than zero on entry, decrement it by
|
||||
one and return true immediately.
|
||||
* If the internal counter is zero on entry, block until awoken by a call to
|
||||
:meth:`~Semaphore.release`. Once awoken (and the counter is greater
|
||||
than 0), decrement the counter by 1 and return true. Exactly one
|
||||
thread will be awoken by each call to :meth:`~Semaphore.release`. The
|
||||
order in which threads are awoken should not be relied on.
|
||||
|
||||
When invoked with *blocking* set to false, do not block. If a call
|
||||
without an argument would block, return false immediately; otherwise,
|
||||
do the same thing as when called without arguments, and return true.
|
||||
without an argument would block, return false immediately; otherwise, do
|
||||
the same thing as when called without arguments, and return true.
|
||||
|
||||
When invoked with a *timeout* other than ``None``, it will block for at
|
||||
most *timeout* seconds. If acquire does not complete successfully in
|
||||
|
|
|
@ -629,13 +629,14 @@ class BaseSemaphoreTests(BaseTestCase):
|
|||
sem = self.semtype(7)
|
||||
sem.acquire()
|
||||
N = 10
|
||||
sem_results = []
|
||||
results1 = []
|
||||
results2 = []
|
||||
phase_num = 0
|
||||
def f():
|
||||
sem.acquire()
|
||||
sem_results.append(sem.acquire())
|
||||
results1.append(phase_num)
|
||||
sem.acquire()
|
||||
sem_results.append(sem.acquire())
|
||||
results2.append(phase_num)
|
||||
b = Bunch(f, 10)
|
||||
b.wait_for_started()
|
||||
|
@ -659,6 +660,7 @@ class BaseSemaphoreTests(BaseTestCase):
|
|||
# Final release, to let the last thread finish
|
||||
sem.release()
|
||||
b.wait_for_finished()
|
||||
self.assertEqual(sem_results, [True] * (6 + 7 + 6 + 1))
|
||||
|
||||
def test_try_acquire(self):
|
||||
sem = self.semtype(2)
|
||||
|
|
Loading…
Reference in New Issue