Question about None

S

Steven D'Aprano

Steven D'Aprano said:
So-called "vacuous truth". It's often useful to have all([]) return
true, but it's not *always* useful -- there are reasonable cases where
the opposite behaviour would be useful:

if all(the evidence points to the Defendant's guilt) then:
the Defendant is guilty
execute(the Defendant)

sadly means that if there is no evidence that a crime has been
committed, the person accused of committing the imaginary crime will be
executed.

This is a bad example. Someone is not convicted of a crime just because
all the available evidence points towards their guilt. There may be
very little evidence altogether, or it might just be circumstancial, or
unconvincing. Even though it may all point towards the defendent's
guilt, it doesn't mean they will be convicted. There needs to be enough
evidence to convince the jury. So it would be something like:

if sum(guilt_weight(e) for e in evidence) > GUILT_THRESHOLD:
the defendant is guilty
...

Not all trials are jury trials, and not all cultures have a presumption
of innocence.

There are, in fact, many places where the government and police think
little of falsifying evidence to convict innocent people, including
people that they know are innocent of any crime (an extreme case was
Stalin's show trials). But as far as I know, nobody ever argues that
people are guilty based on the principle of Vacuous Truth: everybody
agrees that if there is no evidence of a crime, the person should be
considered innocent rather than guilty. Even Stalin manufactured evidence
of crimes. (In most cases, that evidence was to torture people into
confessing to crimes that did not, in fact, take place.)

To put it another way, logically:

all(the evidence is true)
not any(the evidence is false)

should be considered identical, but in practice, we treat:

evidence = [] # evidence of a crime
all(evidence)

as false instead of true, even in places with no presumption of innocence.

While:

not any(map(operator.not_, evidence))

is also treated as false.


In any case, I'm not arguing against vacuous truth -- it's clearly the
right way to deal with empty sets *nearly always*. But it isn't entirely
straight-forward, and leads to some difficulties, such as a vacuous truth
X implies both Y and not Y at the same time.
 
S

Steven D'Aprano

Steven said:
So-called "vacuous truth". It's often useful to have all([]) return
true, but it's not *always* useful -- there are reasonable cases where
the opposite behaviour would be useful:
[...]
It seems to me that the absurd conclusion implied by the theorem
invalidates the theorem rather than supporting your point.

I wouldn't go so far as to say the vacuous truth theorem ("empty
statements are true") is invalidated. The Wikipedia article discusses
various reasons why it's more correct (or at least more useful) to treat
vacuous statements as true:

http://en.wikipedia.org/wiki/Vacuous_truth

But it's not without difficulties -- however those difficulties are
smaller than those if you take vacuous statements as false in general.

[...]
Try finding another 'reasonable case'.

Any time you do something like:

if not x and all(x):
process(x)


instead of just:

if all(x):
process(x)


I can't think of a real world example off the top of my head, but here's
a contrived example demonstrating that vacuous truths imply both a fact
and it's opposite:


def startswith(s, chars):
"""Return True if s starts with any of chars."""
for c in chars:
if s.startswith(c): return True
return False


if all([startswith(w, "aeiou") for w in words]):
print "All the words start with vowels."

if all([startswith(w, "bcdfghjklmnpqrstvwxyz") for w in words]):
print "All of the words start with consonants."


If words is empty, this code claims that all of the words start with
vowels as well as starting with consonants.

There are, of course, ways to work around that other than rejecting
vacuous truths. One is to simply use an "elif" for the second test.
 
A

Aaron Brady

Steven D'Aprano wrote:
So-called "vacuous truth". It's often useful to have all([]) return
true, but it's not *always* useful -- there are reasonable cases where
the opposite behaviour would be useful:
[...]
It seems to me that the absurd conclusion implied by the theorem
invalidates the theorem rather than supporting your point.

I wouldn't go so far as to say the vacuous truth theorem ("empty
statements are true") is invalidated. The Wikipedia article discusses
various reasons why it's more correct (or at least more useful) to treat
vacuous statements as true:

http://en.wikipedia.org/wiki/Vacuous_truth

But it's not without difficulties -- however those difficulties are
smaller than those if you take vacuous statements as false in general.
snip

Those difficulties are pretty gaping.

I would start by dividing the natural language 'use cases' of 'if'
statements into imperative and declarative.

Declarative:

If it's raining, it's cloudy.

In this case, the assertion is meant to convey a general, non-
concrete, observation trend across space and time. Its content is a
claim of 100% correlation between two statuses of the real world.

Imperative:

If you're out of bread, go buy some.

Here, the speaker is in a position of authority over the audience, who
will be following his/er commands, and acting under the speaker's
authority. The speaker is meaning to convey conditional instructions,
for a possible circumstance. There is no component of observation or
assertion.

We see this distinction in programming too. Is the user merely
asserting a relation, or defining a procedure?

Implies( Raining( x ), Cloudy( x ) )

or

if OutOfBread( x ):
BuyBread( )

The 'if' statement is counterfactual in its native environment. As
such, natural speakers never use it in vacuous cases, and it's not
naturally defined.

In a mathematical (ideal) environment, its semantics are artificially
constructed like any other math predicate, and proofs involving it
will define its vacuous case, or fail.
 
T

Terry Reedy

Steven said:
Steven said:
So-called "vacuous truth". It's often useful to have all([]) return
true, but it's not *always* useful -- there are reasonable cases where
the opposite behaviour would be useful:
[...]
It seems to me that the absurd conclusion implied by the theorem
invalidates the theorem rather than supporting your point.

I wouldn't go so far as to say the vacuous truth theorem ("empty
statements are true") is invalidated. The Wikipedia article discusses
various reasons why it's more correct (or at least more useful) to treat
vacuous statements as true:

http://en.wikipedia.org/wiki/Vacuous_truth

But it's not without difficulties -- however those difficulties are
smaller than those if you take vacuous statements as false in general.

[...]
Try finding another 'reasonable case'.

Any time you do something like:

if not x and all(x):
process(x)


instead of just:

if all(x):
process(x)


I can't think of a real world example off the top of my head, but here's
a contrived example demonstrating that vacuous truths imply both a fact
and it's opposite:


def startswith(s, chars):
"""Return True if s starts with any of chars."""
for c in chars:
if s.startswith(c): return True
return False


if all([startswith(w, "aeiou") for w in words]):
print "All the words start with vowels."

if all([startswith(w, "bcdfghjklmnpqrstvwxyz") for w in words]):
print "All of the words start with consonants."
If words is empty, this code claims that all of the words start with
vowels as well as starting with consonants.

So? These are true and non-contradictory. They are NOT 'opposites'.
Together they imply that there are are no words in words, which is true.
To paraphrase my response to mel, I believe it was:

[(x in words => x.startswith(vowel)) and
(x in words => x.startswith(nonvowel)) and
x.startswith(vowel) <=> not(x.startswith(nonvowel)]
=> not(x in words)
which is the definition of 'words is the empty set'
by the law of contradiction.

The negation of 'all words starts with vowel' is 'there exists a word
that starts with a non-vowel', which is different from 'all words start
with consonants' since the latter is true when there are no words
whereas the former is not.

Terry Jan Reedy
 
B

Bruno Desthuilliers

John Yeung a écrit :
Because you might want None to behave as though it were nothing at
all.

Paul LaFollette is probably thinking along the lines of formal logic
or set theory. It's a little bit confused because programming isn't
quite the same as math, and so it's a common question when designing
and implementing programming languages how far to take certain
abstractions. In some languages, nil, null, or none will try to
behave as mathematically close to "nothing" (complete absence of
anything) as possible, even though in reality they have to have some
concrete implementation, such as perhaps being a singleton object.
But mathematically speaking, it's intuitive that "nothing" would match
any type.

IOW, what's the OP is after is not the None type, but some yet
unexisting "Anything" type !-)
 
A

Aaron Brady

John Yeung a écrit :

IOW, what's the OP is after is not the None type, but some yet
unexisting "Anything" type !-)

The behaviors of the 'anything' object are a subset of those of any
other object.

I don't believe that 'subset' is a proper characterization of the
relationship between the methods of a subclass and the methods of its
superclass. But 'superset' may be.

Should 'object' inherit from None?
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,968
Messages
2,570,153
Members
46,699
Latest member
AnneRosen

Latest Threads

Top