So, the Python grammar is much stricter than the English
grammar or most natural language grammars. In English, if we say
something nongrammatical like me go to the store, another English speaker
might laugh at us. But they can probably understand what we
meant. In Python, the code must match the language grammar exactly.
Here we saw when we tried to evaluate 2 plus without
the extra operand, we got a syntax error, that means it's
not grammatical. If we said 2 plus to someone in English
well they might be able to figure out that that
means the same thing as 2. In Python it needs to
match the grammar exactly. So now we're going to look at the
Python grammar for arithmetic expressions. We won't see the entire Python
grammar here. But enough to get an idea of why the
expressions we've seen were valid and why the 2 plus is
not. So first of all, an expression is something that has
a value. We're going to start our grammar with an non-terminal expression.
And we can make an expression by combining two expressions
with an operator. This is sort of like the sentence
rule we have for English where we could make a
sentence by combining a subject, a verb and an object.
This is a lot more interesting though, because we have
expressions both on the left side and the right side.
This looks kind of circular. Because we have other rules,
it's not completely circular. This is what's called a recursive definition.
We'll talk a lot more about that in a later
class, in unit six we will, but for now, we're going to
just see how we can use that to make the Python
grammar. And to make a good recursive definition, we need at
least two rules. We need one where we can keep going,
using the same thing on the right side as the left
side. And we need one where we can stop. So, another
thing that an expression can be is a number. And this
is why we can make expressions like 1 plus
1. This expression will become a number which will become
one. The operator will become plus, and the other
expression will become one. So let's write a few more
rules to see how that works. So we can
replace the operator with plus. We can also replace operator
with times. And there's several more operators in Python.
Those are enough for now, we just need those two.
We can also make numbers. And the complete rule
for making numbers is sort of complicated, but let's
assume we know what numbers are. We can make
numbers any number of digits. There different rules to make
all those numbers, but we know what they are.
So, this looks like a very simple grammar. It's
quite small, but it can express infinitely many things.
And the reason for that is because we have expression
on both sides here. That we can replace an
expression with a derivative expression, and keep going. So
here's an example derivation. We can start with expression.
We can follow the rule, replacing that with expression
operator expression. And then, we can follow the rules
again. We can replace the first expression with a
number and replace that number with the actual number
one. And we notice the actual numbers are terminal.
So, once we get to the number one, we're done.
There's no more replacements to do. We can replace the
operator with plus. Plus is also a terminal, and we
can replace this expression with a number, and replace that
number with the number one. So this is how we
got the expression 1 plus 1 in the Python grammar
and that's why that was valid. We can do a
lot more than this though. Instead of replacing this expression
with a number, we can replace this expression with
another expression, operator expression. So we're going to use the
first rule replacing the expression with expression, operator expression
here. I'm going to start abbreviating so Expr is an abbreviation
for expression. Op for operator and Expr but, we're
just using this rule. And now we can do
the same thing again, replacing this expression with a
number and replacing that number, let's say with number two.
We could replace this operator with the multiplication
operator. And we can replace this expression with a
number. Or you could replace it with an
expression, operator, expression. Let's do that, and build increasingly
complicated expressions this way. We can keep doing
this. We are not done until everything is a
terminal. So let's say, we skipped a few steps here, but this could be 3 plus 3.
So this is how we can build up complicated expressions
from very simple rules. So I am going to add one
more rule to our python grammar, that will be enough
to produce all the expressions that we have used so far.
And that rule that we need is for parentheses. And
this is actually quite a simple rule. It just says
we can make an expression by taking any expression we
have and putting parentheses around it. So, this is a pretty
small grammar, but this is actually grammar that's powerful enough
to produce all the Python expressions we've seen so far.
As well as infinitely many different expressions. We're not going to
cover the entire Python grammar this way, but this should
give you an idea of the power of writing our
grammar this way. So we're going to have a quiz to
see that everyone understands the grammar. So the question is
which of the following are valid Python expressions that can
be produced starting from expression using the
grammar rules. So here are the choices; there
are five possibilities, check all the ones that
are valid expressions that can be produced from
this grammar starting from expression. You can try
your answers in the Python interpreter if you
want, but first see if you can figure it out for yourself, which ones are valid.