<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Issue 3402: Wording for negative_binomial_distribution is unclear as a consequence of LWG 2406 resolution</title>
<meta property="og:title" content="Issue 3402: Wording for negative_binomial_distribution is unclear as a consequence of LWG 2406 resolution">
<meta property="og:description" content="C++ library issue. Status: New">
<meta property="og:url" content="https://cplusplus.github.io/LWG/issue3402.html">
<meta property="og:type" content="website">
<meta property="og:image" content="http://cplusplus.github.io/LWG/images/cpp_logo.png">
<meta property="og:image:alt" content="C++ logo">
<style>
  p {text-align:justify}
  li {text-align:justify}
  pre code.backtick::before { content: "`" }
  pre code.backtick::after { content: "`" }
  blockquote.note
  {
    background-color:#E0E0E0;
    padding-left: 15px;
    padding-right: 15px;
    padding-top: 1px;
    padding-bottom: 1px;
  }
  ins {background-color:#A0FFA0}
  del {background-color:#FFA0A0}
  table.issues-index { border: 1px solid; border-collapse: collapse; }
  table.issues-index th { text-align: center; padding: 4px; border: 1px solid; }
  table.issues-index td { padding: 4px; border: 1px solid; }
  table.issues-index td:nth-child(1) { text-align: right; }
  table.issues-index td:nth-child(2) { text-align: left; }
  table.issues-index td:nth-child(3) { text-align: left; }
  table.issues-index td:nth-child(4) { text-align: left; }
  table.issues-index td:nth-child(5) { text-align: center; }
  table.issues-index td:nth-child(6) { text-align: center; }
  table.issues-index td:nth-child(7) { text-align: left; }
  table.issues-index td:nth-child(5) span.no-pr { color: red; }
  @media (prefers-color-scheme: dark) {
     html {
        color: #ddd;
        background-color: black;
     }
     ins {
        background-color: #225522
     }
     del {
        background-color: #662222
     }
     a {
        color: #6af
     }
     a:visited {
        color: #6af
     }
     blockquote.note
     {
        background-color: rgba(255, 255, 255, .10)
     }
  }
</style>
</head>
<body>
<hr>
<p><em>This page is a snapshot from the LWG issues list, see the <a href="lwg-active.html">Library Active Issues List</a> for more information and the meaning of <a href="lwg-active.html#New">New</a> status.</em></p>
<h3 id="3402"><a href="lwg-active.html#3402">3402</a>. Wording for <code>negative_binomial_distribution</code> is unclear as a consequence of LWG 2406 resolution</h3>
<p><b>Section:</b> 29.5.9.3.4 <a href="https://wg21.link/rand.dist.bern.negbin">[rand.dist.bern.negbin]</a> <b>Status:</b> <a href="lwg-active.html#New">New</a>
 <b>Submitter:</b> Ahti Lepp&auml;nen <b>Opened:</b> 2020-02-17 <b>Last modified:</b> 2020-03-11</p>
<p><b>Priority: </b>3
</p>
<p><b>View all other</b> <a href="lwg-index.html#rand.dist.bern.negbin">issues</a> in [rand.dist.bern.negbin].</p>
<p><b>View all issues with</b> <a href="lwg-status.html#New">New</a> status.</p>
<p><b>Discussion:</b></p>
<p>
This issue has been created because a corresponding 
<a href="https://github.com/cplusplus/draft/issues/3606">editorial change request</a> had been rejected.
<p/>
The resolution of LWG <a href="lwg-defects.html#2406" title="negative_binomial_distribution should reject p == 1 (Status: C++17)">2406</a><sup><a href="https://cplusplus.github.io/LWG/issue2406" title="Latest snapshot">(i)</a></sup> added a note to the definition of <code>negative_binomial_distribution</code>:
</p>
<blockquote style="border-left: 3px solid #ccc;padding-left: 15px;">
<p>
[<i>Note</i>: This implies that <math xmlns="http://www.w3.org/1998/Math/MathML">
<mi>P</mi><mrow><mo>(</mo><mi>i</mi><mo>|</mo><mi>k</mi><mo>,</mo><mi>p</mi><mo>)</mo></mrow> 
</math> is undefined when <code>p == 1</code>. &mdash; <i>end note</i>]
</p>
</blockquote>
<p>
This issue argues that the note is invalid as are the premises on which LWG 2406 was based 
on. It's also argued that current normative standard text allowing <code>p == 1</code> is valid 
both conceptually and mathematically, and that it follows existing conventions in other software.
<p/>
Problems with the added note:
</p>
<ul>
<li><p>Why does <code>p == 1</code> imply that <math xmlns="http://www.w3.org/1998/Math/MathML">
<mi>P</mi><mrow><mo>(</mo><mi>i</mi><mo>|</mo><mi>k</mi><mo>,</mo><mi>p</mi><mo>)</mo></mrow> 
</math> is undefined? The only questionable factor in the definition of 
<math xmlns="http://www.w3.org/1998/Math/MathML"><mi>P</mi><mrow><mo>(</mo><mi>i</mi><mo>|</mo>
<mi>k</mi><mo>,</mo><mi>p</mi><mo>)</mo></mrow></math> seems to be that in case of 
<code>p == 1</code>, the factor <code>(1 - p)<sup>i</sup></code> leads to <code>0<sup>0</sup></code> 
when <code>i == 0</code>. While it is true that there's 
<a href="https://en.wikipedia.org/wiki/Zero_to_the_power_of_zero">no generally accepted convention</a> 
what this means, <code>std::binomial_distribution</code> already uses the common convention 
<code>0<sup>0</sup> == 1</code> (e.g. with <code>p == 1 &amp;&amp; t == i</code>, 
<math xmlns="http://www.w3.org/1998/Math/MathML">
<mi>P</mi><mrow><mo>(</mo><mi>i</mi><mo>|</mo><mi>k</mi><mo>,</mo><mi>p</mi><mo>)</mo></mrow> 
</math> leads to <code>0<sup>0</sup></code>)</p></li>
<li><p>Even if the term was undefined mathematically, does a non-normative note of
mathematical term being undefined mean that the behaviour of the program is
undefined (instead of e.g. resulting to NaN) even when no preconditions are violated?</p></li>
<li><p>The note has lead to unclear situation of being able to construct a
distribution object, but calling <code>operator()</code> might lead to undefined behaviour
even though no preconditions are violated: for example the 
<a href="https://en.cppreference.com/mwiki/index.php?title=cpp/numeric/random/negative_binomial_distribution/negative_binomial_distribution&amp;oldid=102755">cppreference.com notes</a> that 
</p>
<blockquote style="border-left: 3px solid #ccc;padding-left: 15px;">
<p>
If <code>p == 1</code>, subsequent calls to the <code>operator()</code> overload that does not
accept a <code>param_type</code> object will cause undefined behavior.
</p>
</blockquote>
</li>
</ul>
<p>
Invalidity of premises of LWG 2406:
</p>
<ul>
<li>
<blockquote style="border-left: 3px solid #ccc;padding-left: 15px;">
<p>
For <code>p == 1</code>, this is "<code>* 1^k * 0^i</code>", so every integer 
<code>i &gt;= 0</code> is produced with zero probability. (Let's avoid thinking about 
<code>0^0</code>.)
</p>
</blockquote>
<ul>
<li><p>This is contradictory: first assuming that <code>0^i == 0</code> for all 
<code>i &gt;= 0</code> (implying that <code>0^0 == 0</code>), but then comments not to 
think about <code>0^0</code>. The very essence of the issue is interpretation of 
<code>0^0</code> and given the definition of <code>binomial_distribution</code>, 
where <code>0^0 == 1</code>, the claim "so every integer <code>i &gt;= 0</code> is 
produced with zero probability" can be considered faulty.
</p></li>
</ul>
</li>
<li>
<blockquote style="border-left: 3px solid #ccc;padding-left: 15px;">
<p>
Wikipedia states that <code>p</code> must be within <code>(0, 1)</code>, exclusive on both sides.
</p>
</blockquote>
<ul>
<li><p>
I cannot find any mention of this in the 
<a href="https://en.wikipedia.org/w/index.php?title=Negative_binomial_distribution&amp;oldid=611204120">Wikipedia's
version as of 2014-06-02</a> (i.e. around the time when LWG 2406 was opened). Note that 
the Wikipedia's version is not the same as in C++ standard; in Wikipedia, <code>p</code> 
parameter is the same &mdash; i.e. the probability of success &mdash; but the integer parameter 
(<code>&gt; 0</code>) is <em>number of failures</em>, while in C++ it is the <em>number of successes</em>. 
In the failure formulation <code>p == 1</code> is indeed invalid for essentially the same reason why 
<code>p == 0</code> is invalid for the C++ definition (i.e. leads to 
<math xmlns="http://www.w3.org/1998/Math/MathML">
<mi>P</mi><mrow><mo>(</mo><mi>i</mi><mo>|</mo><mi>k</mi><mo>,</mo><mi>p</mi><mo>)</mo></mrow> 
</math><code> == 0</code> for all <code>i</code>).
</p></li>
</ul>
</li>
</ul>
<p>
Validity of <code>p == 1</code>:
</p>
<ul>
<li>
<blockquote style="border-left: 3px solid #ccc;padding-left: 15px;">
<p>[&hellip;] distribution of the number of failures in a sequence of trials with
success probability <code>p</code> before <code>n</code> successes occur.
</p>
</blockquote>
<p>
(from <a href="https://reference.wolfram.com/language/ref/NegativeBinomialDistribution.html">
Wolfram documentation</a>). When <code>p == 1</code>, this means that trial always succeeds, 
so it's obvious that the probability to get 0 failures is 1, and the probability for 
<code>i &gt; 0</code> failures is 0. This is exactly what the mathematical definition in
29.5.9.3.4 <a href="https://wg21.link/rand.dist.bern.negbin">[rand.dist.bern.negbin]</a> gives with convention <code>0<sup>0</sup> = 1</code> 
when <code>p == 1</code>.
</p>
</li>
<li><p>
Software such as 
<a href="https://reference.wolfram.com/language/ref/NegativeBinomialDistribution.html">Mathematica</a>,
<a href="https://mathworks.com/help/stats/prob.negativebinomialdistribution.html">Matlab</a>
and <a href="http://search.r-project.org/R/library/stats/html/NegBinomial.html">R</a> all
accept <code>p == 1</code> for negative binomial distribution and they use the integer parameter 
as number of successes like the C++ standard.
</p></li>
</ul>
<p>
What comes to the reasons why <code>p == 1</code> could have been considered invalid, it
seems that major implementations &mdash; namely 
<a href="https://github.com/gcc-mirror/gcc/blob/07c86323a199ca15177d99ad6c488b8f5fb5c729/libstdc%2B%2B-v3/include/bits/random.h#L4240">libstd++</a>,
<a href="https://github.com/llvm/llvm-project/blob/d081962dead08ef0982081e78d679dd609947ca5/libcxx/include/random#L5233">libc++</a> and 
<a href="https://github.com/microsoft/STL/blob/0e336ac7379c5b4d80280fa828b1a3bccc351d27/stl/inc/random#L4350">MSVC
standard library</a> &mdash; are using <code>std::gamma_distribution</code> in 
<code>std::negative_binomial_distribution</code> and passing <code>(1 - p)/p</code> as the second argument
of <code>std::gamma_distribution</code>. Case <code>p == 1</code> is not checked leading to violation of
precondition of <code>std::gamma_distribution</code>, which requires argument to be <code>&gt; 0</code>.
<p/>
For these reasons the note added by resolution of LWG 2406 seems invalid and could be considered for 
removal. However given the current status and history regarding handling of case <code>p == 1</code>, 
removing the note might not be the only option to consider.
</p>

<p><i>[2020-03-11 Issue Prioritization]</i></p>

<p>Priority to 3 and hand over to SG6 after reflector discussion.</p>


<p id="res-3402"><b>Proposed resolution:</b></p>




</body>
</html>
