WEBVTT

00:00:07.192 --> 00:00:08.566
SRINI DEVADAS:
Morning, everyone.

00:00:08.566 --> 00:00:12.830
Welcome to 6.S095.

00:00:12.830 --> 00:00:14.520
Thanks for registering
for this class.

00:00:14.520 --> 00:00:15.760
I hope you like it.

00:00:15.760 --> 00:00:17.180
My name is Srini Devadas.

00:00:17.180 --> 00:00:22.900
I'm a professor of computer
science at MIT, obviously,

00:00:22.900 --> 00:00:26.275
and I've been teaching
at MIT for 30 years.

00:00:26.275 --> 00:00:28.810
So I've been at it for a while.

00:00:28.810 --> 00:00:30.730
The reason I'm
teaching this IAP class

00:00:30.730 --> 00:00:36.550
is because I want to try
out this way of teaching

00:00:36.550 --> 00:00:40.750
programming that starts
with the recreational world

00:00:40.750 --> 00:00:44.080
of mathematical puzzles,
algorithmic puzzles,

00:00:44.080 --> 00:00:48.760
and I want to connect it
up to writing programs.

00:00:48.760 --> 00:00:54.090
And I have taught this
material before in 6.009

00:00:54.090 --> 00:00:57.620
that I think some of
you are registered for,

00:00:57.620 --> 00:01:01.510
but I wanted to teach it
in a more interactive,

00:01:01.510 --> 00:01:02.860
informal setting.

00:01:02.860 --> 00:01:06.250
And I should mention
that I wrote a book

00:01:06.250 --> 00:01:09.970
on this, which is a book
that's recommended, though not

00:01:09.970 --> 00:01:11.680
required, for 6.009.

00:01:11.680 --> 00:01:15.460
And so you might see
this in the MIT Press

00:01:15.460 --> 00:01:17.440
Bookstore and other places.

00:01:17.440 --> 00:01:21.120
And most of the material
I'm going to cover here

00:01:21.120 --> 00:01:22.510
is from the book.

00:01:22.510 --> 00:01:24.700
But I don't want
you to read the book

00:01:24.700 --> 00:01:29.710
because I want you to listen to
my explanations for the puzzles

00:01:29.710 --> 00:01:32.470
and try and think
of the solutions

00:01:32.470 --> 00:01:37.810
yourself and then obviously
do some amount of coding

00:01:37.810 --> 00:01:40.600
not during lecture but offline.

00:01:40.600 --> 00:01:43.120
And I'll show you some
solutions to the puzzles,

00:01:43.120 --> 00:01:45.430
and there will be
some exercises.

00:01:45.430 --> 00:01:48.970
So I don't want to spend a
whole lot of time on logistics.

00:01:48.970 --> 00:01:52.690
This is an IAP class,
as I mentioned.

00:01:52.690 --> 00:01:55.810
I'd like this to be
informal and relaxed.

00:01:55.810 --> 00:01:59.920
So we meet every
day for two weeks.

00:01:59.920 --> 00:02:01.630
We have the holiday
coming up on Monday,

00:02:01.630 --> 00:02:06.930
so we'll have nine total
lectures roughly for an hour.

00:02:06.930 --> 00:02:10.509
It might spill over, but
hopefully, you'll be OK with it

00:02:10.509 --> 00:02:14.110
because you don't have another
class to go to at noon.

00:02:14.110 --> 00:02:16.870
And if you do,
well, let me know,

00:02:16.870 --> 00:02:20.920
and I'll give you that
five minutes of overflow

00:02:20.920 --> 00:02:25.720
personally at a time
of your choosing.

00:02:25.720 --> 00:02:29.780
But hopefully,
I'll keep on time.

00:02:29.780 --> 00:02:32.930
And in terms of work,
this is a pass/fail.

00:02:32.930 --> 00:02:34.900
It's a for-credit class.

00:02:34.900 --> 00:02:37.540
I know some of you may be
listeners, but some of you

00:02:37.540 --> 00:02:38.710
are registered for it.

00:02:38.710 --> 00:02:40.660
So I'll have to
assign you a grade,

00:02:40.660 --> 00:02:42.149
so there will be some exercises.

00:02:42.149 --> 00:02:43.690
And I'm going to
make it very simple.

00:02:46.230 --> 00:02:48.320
There'll be exercises
up on the website.

00:02:48.320 --> 00:02:51.550
They'll be due two days
from when I put them up.

00:02:51.550 --> 00:02:54.070
And you'll have options
in terms of whether to do

00:02:54.070 --> 00:02:56.590
a really simple
exercise that's probably

00:02:56.590 --> 00:03:00.570
going to take about five
minutes or do something harder.

00:03:00.570 --> 00:03:02.050
And for each of
the puzzles, there

00:03:02.050 --> 00:03:05.650
are two or three exercises,
and you get to do all of them

00:03:05.650 --> 00:03:06.560
if you want.

00:03:06.560 --> 00:03:11.010
You can choose to
do one or the other.

00:03:11.010 --> 00:03:15.340
I'm going to have office hours
every day from 1:00 to 2:00.

00:03:15.340 --> 00:03:18.400
I don't plan on putting
solutions up to the exercises.

00:03:18.400 --> 00:03:21.390
The solutions to the
puzzles themselves,

00:03:21.390 --> 00:03:23.350
they'll be shown
mostly in lecture

00:03:23.350 --> 00:03:26.410
and put up on the
Stellar website,

00:03:26.410 --> 00:03:28.920
but the solutions
to the exercises,

00:03:28.920 --> 00:03:30.070
I'm not going to put up.

00:03:30.070 --> 00:03:32.290
But if you ever get
stuck, well, that's

00:03:32.290 --> 00:03:33.880
what office hours are for.

00:03:33.880 --> 00:03:36.960
And if you can't
solve the exercises,

00:03:36.960 --> 00:03:39.410
I'll help to solve them.

00:03:39.410 --> 00:03:42.070
So with that,
without further ado,

00:03:42.070 --> 00:03:45.280
let's dive in and
talk about puzzles

00:03:45.280 --> 00:03:50.050
and solving puzzles using
algorithms and then programs.

00:03:50.050 --> 00:03:52.030
I'd really like this
to be interactive,

00:03:52.030 --> 00:03:58.420
so please ask questions
and suggest solutions

00:03:58.420 --> 00:03:59.510
that I haven't thought of.

00:03:59.510 --> 00:04:00.250
That'd be great.

00:04:00.250 --> 00:04:02.300
In my second edition,
whenever that is,

00:04:02.300 --> 00:04:04.810
you'll get credit for that.

00:04:04.810 --> 00:04:14.490
So the first puzzle, I
tried to have, I don't know,

00:04:14.490 --> 00:04:18.250
funny titles for all
of these puzzles--

00:04:18.250 --> 00:04:19.370
intriguing.

00:04:19.370 --> 00:04:22.900
And so the first puzzle is
called "You Will All Conform."

00:04:22.900 --> 00:04:25.240
This is really a warm-up puzzle.

00:04:25.240 --> 00:04:27.867
As you'll see-- this
is true for any class--

00:04:27.867 --> 00:04:30.200
things are going to get more
complicated as we go along.

00:04:30.200 --> 00:04:33.370
So we'll probably do 10 or 12
puzzles in the next two weeks.

00:04:33.370 --> 00:04:39.860
And by the end, you're going
to see things like memoization

00:04:39.860 --> 00:04:41.620
and dynamic
programming and things

00:04:41.620 --> 00:04:44.390
like that towards
the end of next week.

00:04:44.390 --> 00:04:46.990
And if you don't know
what those mean, well,

00:04:46.990 --> 00:04:50.320
that's great because
hopefully, you

00:04:50.320 --> 00:04:52.630
will know by the end
of the two weeks.

00:04:52.630 --> 00:04:56.570
And a lot of these things
are algorithmic insights,

00:04:56.570 --> 00:05:02.390
are insights that will help you
in Course 6 classes, for sure,

00:05:02.390 --> 00:05:10.080
and perhaps even if you follow
a career outside of Course 6.

00:05:10.080 --> 00:05:16.820
So this particular puzzle is, as
I said, a fairly simple puzzle,

00:05:16.820 --> 00:05:18.470
at least to describe.

00:05:18.470 --> 00:05:22.170
And the setting is as follows.

00:05:22.170 --> 00:05:25.004
So you're a gatekeeper
at a baseball game.

00:05:25.004 --> 00:05:26.420
We'll just call
it a baseball game

00:05:26.420 --> 00:05:28.100
because baseball
players wear caps,

00:05:28.100 --> 00:05:33.019
and most people are
watching games with caps on.

00:05:33.019 --> 00:05:35.060
And so you're a gatekeeper,
and there are a bunch

00:05:35.060 --> 00:05:37.820
of people standing in line.

00:05:37.820 --> 00:05:41.390
Let's just say each of
them knows their number.

00:05:41.390 --> 00:05:43.520
And this is Python,
so the number

00:05:43.520 --> 00:05:46.790
starts at 0 as opposed to 1.

00:05:46.790 --> 00:05:48.410
And there are a
whole bunch of people

00:05:48.410 --> 00:05:54.050
standing in line waiting to
get in, and they all have caps.

00:05:54.050 --> 00:05:57.430
And some of them are
wearing their caps forward,

00:05:57.430 --> 00:06:00.305
so with the--

00:06:00.305 --> 00:06:02.090
I guess, what do you call it?

00:06:02.090 --> 00:06:05.150
What's the front
of the cap called?

00:06:05.150 --> 00:06:09.940
The shade-- the thing that
gives you shade up front.

00:06:09.940 --> 00:06:13.350
And so we just say--

00:06:13.350 --> 00:06:14.870
let me try and draw this out.

00:06:14.870 --> 00:06:18.920
So this person is wearing
his cap like that,

00:06:18.920 --> 00:06:23.820
and this lady here is
wearing her cap like this.

00:06:23.820 --> 00:06:27.200
So that's forwards,
and that's backwards.

00:06:29.990 --> 00:06:37.740
So your job here
is straightforward.

00:06:37.740 --> 00:06:42.500
You can only let all of
these people into line--

00:06:42.500 --> 00:06:49.930
sorry-- into the stadium who
are in line if they all conform.

00:06:49.930 --> 00:06:52.490
So they all have
to wear their caps

00:06:52.490 --> 00:06:55.640
in a particular orientation,
and you don't particularly

00:06:55.640 --> 00:06:57.980
care which one.

00:06:57.980 --> 00:07:00.200
And so they all
have to be forwards,

00:07:00.200 --> 00:07:03.920
all, let's say, 13 of them.

00:07:03.920 --> 00:07:06.590
Or they all have
to be backwards.

00:07:06.590 --> 00:07:11.330
Now, all of them know
their position on the line.

00:07:11.330 --> 00:07:14.630
So this person knows
that his position is 0,

00:07:14.630 --> 00:07:16.670
this lady here knows
that her position

00:07:16.670 --> 00:07:19.640
is 1, et cetera, et cetera.

00:07:19.640 --> 00:07:24.830
And so obviously, you'd like
to minimize the amount of work

00:07:24.830 --> 00:07:30.560
that you do, and you
could certainly choose--

00:07:30.560 --> 00:07:32.720
let's say you want
everyone to be forwards.

00:07:32.720 --> 00:07:36.740
You could say, hey, lady in
position 1, flip your cap.

00:07:36.740 --> 00:07:39.350
Oh, I should mention
something that is important.

00:07:39.350 --> 00:07:41.240
So people have a
different definition

00:07:41.240 --> 00:07:42.860
of forwards and backwards.

00:07:42.860 --> 00:07:47.060
It's sort of what's natural
and what's unnatural to them.

00:07:47.060 --> 00:07:53.090
So we think that this person
has his cap on forwards.

00:07:53.090 --> 00:07:55.160
But for all you know, he
thinks he's got his cap

00:07:55.160 --> 00:07:57.050
on backwards or vice versa.

00:07:57.050 --> 00:08:00.830
So you can't assume
that the definition

00:08:00.830 --> 00:08:04.880
of "forwards" and "backwards" is
identical for all of the people

00:08:04.880 --> 00:08:09.170
in line and really is the
same as your definition.

00:08:09.170 --> 00:08:11.090
It seems kind of unreasonable.

00:08:11.090 --> 00:08:17.677
Hey, this is a puzzle, so
let's not argue about that.

00:08:17.677 --> 00:08:19.760
We can argue about other
things, like how to write

00:08:19.760 --> 00:08:22.790
Python programs properly.

00:08:22.790 --> 00:08:24.860
So what you have
to do now is you

00:08:24.860 --> 00:08:30.020
have to call out commands
that correspond to saying,

00:08:30.020 --> 00:08:34.549
person in position
0, flip your cap.

00:08:34.549 --> 00:08:35.900
That's all you can say.

00:08:35.900 --> 00:08:38.690
You can just say, flip your cap.

00:08:38.690 --> 00:08:41.780
You can obviously see how
these caps are oriented,

00:08:41.780 --> 00:08:43.850
and you can ask--

00:08:43.850 --> 00:08:45.870
let's say that you had
something like that.

00:08:45.870 --> 00:08:49.640
I'm just making this up as
I go along, in terms of I'm

00:08:49.640 --> 00:08:52.160
not going to draw
all the caps here.

00:08:52.160 --> 00:08:55.950
But this is what it looks like.

00:08:55.950 --> 00:09:01.010
And so according to you,
you see F, B, B, in terms

00:09:01.010 --> 00:09:02.540
of Forwards and Backwards.

00:09:02.540 --> 00:09:06.230
And let's say you decide
that you want everyone

00:09:06.230 --> 00:09:10.290
to have their cap on forwards.

00:09:10.290 --> 00:09:14.870
Then you could say, person
in position 1, flip your cap.

00:09:14.870 --> 00:09:17.240
Person in position
2, flip your cap.

00:09:17.240 --> 00:09:21.230
And then person in
position 4, 7, et cetera.

00:09:21.230 --> 00:09:23.900
And you want to make
it easier on yourself

00:09:23.900 --> 00:09:30.260
because people do know their
indices, their positions

00:09:30.260 --> 00:09:31.310
in line.

00:09:31.310 --> 00:09:33.560
And so to save
yourself some trouble,

00:09:33.560 --> 00:09:37.160
you could say, people in
positions 1 through 2--

00:09:37.160 --> 00:09:40.910
and the implication is that
it's inclusive-- flip your caps.

00:09:40.910 --> 00:09:44.540
And so that takes
care of these two.

00:09:44.540 --> 00:09:53.930
And perhaps 8 here and 9
had their caps on backwards,

00:09:53.930 --> 00:09:57.950
and you could say, people
in positions 7 through 9,

00:09:57.950 --> 00:09:59.540
flip your caps.

00:09:59.540 --> 00:10:01.220
So in this particular
example, assuming

00:10:01.220 --> 00:10:05.630
that things ended with 10
people in line, 0 through 9,

00:10:05.630 --> 00:10:10.610
you could get away
with three commands.

00:10:10.610 --> 00:10:14.180
You could say, 1 through 2--

00:10:14.180 --> 00:10:18.180
and the implication, as I
said, is this is inclusive--

00:10:18.180 --> 00:10:19.910
flip.

00:10:19.910 --> 00:10:25.040
And then you could say, 4, flip.

00:10:25.040 --> 00:10:32.870
And then you could
say, 7 through 9, flip.

00:10:32.870 --> 00:10:36.620
And if you did it
the other way, you

00:10:36.620 --> 00:10:39.290
could also say,
person at 0, flip,

00:10:39.290 --> 00:10:41.050
and so this would go backwards.

00:10:41.050 --> 00:10:43.190
Person at 3, flip.

00:10:43.190 --> 00:10:45.020
Obviously, you can't
say, 0 through 3

00:10:45.020 --> 00:10:46.760
because that would be wrong.

00:10:46.760 --> 00:10:51.540
And then you could
say 5 through 6 here.

00:10:51.540 --> 00:10:57.980
So you would get three
commands in that case, as well.

00:10:57.980 --> 00:11:03.170
But if in fact, for
argument's sake, let's

00:11:03.170 --> 00:11:08.950
just say that I'm going
to just turn this into 10

00:11:08.950 --> 00:11:12.630
and put an F down here.

00:11:12.630 --> 00:11:17.190
Then these three
commands would still

00:11:17.190 --> 00:11:24.300
work if you wanted to focus
on the B's, on the Backwards

00:11:24.300 --> 00:11:27.300
people, and make them
make them go forwards.

00:11:27.300 --> 00:11:29.580
But if you wanted to make
all of the forward people

00:11:29.580 --> 00:11:38.300
go backwards, you would need
1, 2, 3, 4, four commands.

00:11:38.300 --> 00:11:39.960
So in this particular
case, you're

00:11:39.960 --> 00:11:43.950
better off doing that as
opposed to doing four commands.

00:11:43.950 --> 00:11:51.000
So first straightforward
question is--

00:11:51.000 --> 00:11:53.150
and I'm not talking
about code yet--

00:11:53.150 --> 00:11:56.610
algorithmically, just
in terms of pseudocode--

00:11:56.610 --> 00:12:00.060
and I'm happy with English--

00:12:00.060 --> 00:12:05.340
how would you determine the
minimum set of commands given

00:12:05.340 --> 00:12:07.520
a particular set of people?

00:12:07.520 --> 00:12:09.960
There's an arbitrary
set of people.

00:12:09.960 --> 00:12:14.010
You want to make sure that you
have the absolute minimum set

00:12:14.010 --> 00:12:18.007
of commands, and you're going
to have to use these intervals.

00:12:18.007 --> 00:12:19.590
So you definitely
want to look for all

00:12:19.590 --> 00:12:21.381
the contiguous intervals
because obviously,

00:12:21.381 --> 00:12:24.540
if you say 1 followed and then
that's a separate command, then

00:12:24.540 --> 00:12:28.170
you say 2 and that's
a separate command,

00:12:28.170 --> 00:12:32.670
you end up having more
commands than necessary.

00:12:32.670 --> 00:12:35.830
So anyone want to tell
me I guess roughly,

00:12:35.830 --> 00:12:41.280
in terms of pseudocode,
how this would work?

00:12:41.280 --> 00:12:42.462
Yeah, go ahead.

00:12:42.462 --> 00:12:45.062
AUDIENCE: Well, you
could go down the line

00:12:45.062 --> 00:12:48.205
and look at the groups.

00:12:48.205 --> 00:12:51.187
So start with the 0.

00:12:51.187 --> 00:12:52.675
You've got to write 0.

00:12:52.675 --> 00:12:53.175
Group them.

00:12:53.175 --> 00:12:55.570
And then whatever
the second one is--

00:12:55.570 --> 00:13:00.990
so whatever the second
group is, if it's F or B,

00:13:00.990 --> 00:13:03.066
those are the ones
that need to be flipped

00:13:03.066 --> 00:13:06.210
because that's going to be the
minimum number of commands.

00:13:06.210 --> 00:13:10.300
And then so from what
you pass through,

00:13:10.300 --> 00:13:13.765
whenever you get to those,
you just tell them to flip.

00:13:13.765 --> 00:13:14.890
SRINI DEVADAS: Sounds good.

00:13:14.890 --> 00:13:16.150
Do you have anything
to add to that?

00:13:16.150 --> 00:13:16.691
AUDIENCE: No.

00:13:16.691 --> 00:13:19.391
I was going to say, you
find the backwards interval

00:13:19.391 --> 00:13:20.510
or forward interval.

00:13:20.510 --> 00:13:23.615
And whichever is
the lower, then--

00:13:23.615 --> 00:13:24.490
SRINI DEVADAS: Lower.

00:13:24.490 --> 00:13:25.000
That's good.

00:13:25.000 --> 00:13:25.240
Good.

00:13:25.240 --> 00:13:25.740
Excellent.

00:13:25.740 --> 00:13:27.280
And so both of you had it right.

00:13:27.280 --> 00:13:31.140
So let me explain what these two
gentlemen-- what was your name?

00:13:31.140 --> 00:13:31.890
AUDIENCE: Ganatra.

00:13:31.890 --> 00:13:32.960
SRINI DEVADAS: Ganatra?

00:13:32.960 --> 00:13:33.643
Yours?

00:13:33.643 --> 00:13:34.510
AUDIENCE: Fadi.

00:13:34.510 --> 00:13:35.664
SRINI DEVADAS: Fadi?

00:13:35.664 --> 00:13:36.490
AUDIENCE: Yeah.

00:13:36.490 --> 00:13:39.650
SRINI DEVADAS: So
Ganatra and Fadi said--

00:13:39.650 --> 00:13:43.390
so basically, this
is, as I said,

00:13:43.390 --> 00:13:47.470
the natural algorithm
that you would use.

00:13:47.470 --> 00:13:49.600
The natural algorithm
would be that you

00:13:49.600 --> 00:13:53.500
walk through this
list, and you start

00:13:53.500 --> 00:13:55.420
computing what I would
call-- you called it

00:13:55.420 --> 00:13:56.200
"groups," Ganatra.

00:13:56.200 --> 00:13:59.470
But I'd call them
"intervals," and an interval

00:13:59.470 --> 00:14:01.750
is something that is unbroken.

00:14:01.750 --> 00:14:02.860
It's contiguous.

00:14:02.860 --> 00:14:05.380
It's a contiguous
set of people who

00:14:05.380 --> 00:14:08.650
all have their caps in
the same orientation,

00:14:08.650 --> 00:14:10.530
be it forward or backwards.

00:14:10.530 --> 00:14:16.720
And what you would do in this
case is you would compute the--

00:14:16.720 --> 00:14:19.810
you would say, I want to look
at the forward intervals.

00:14:19.810 --> 00:14:21.390
And the forward
intervals would be 0,

00:14:21.390 --> 00:14:24.340
0 because that's essentially
what you have in here.

00:14:24.340 --> 00:14:27.730
And going through that
list, you would also say,

00:14:27.730 --> 00:14:30.010
I'm going to be computing
the backward intervals.

00:14:30.010 --> 00:14:35.110
And in this case, you discover
1, 2 as the backwards interval.

00:14:35.110 --> 00:14:37.150
So I'm going to write
them out like that.

00:14:37.150 --> 00:14:39.850
And in general, in the
mathematical notation,

00:14:39.850 --> 00:14:44.640
when you put square brackets,
these are closed intervals.

00:14:44.640 --> 00:14:46.630
So 0 is included.

00:14:46.630 --> 00:14:48.252
And we're going to
see a puzzle where

00:14:48.252 --> 00:14:50.210
you might see something
a little bit different,

00:14:50.210 --> 00:14:51.650
so I wanted to point that out.

00:14:51.650 --> 00:14:54.610
So 1, 2 are both
inside this interval.

00:14:54.610 --> 00:14:57.730
And these two you
would generate as you

00:14:57.730 --> 00:14:59.380
would go through the
list, and then you

00:14:59.380 --> 00:15:03.010
would generate 3, 3 over here.

00:15:03.010 --> 00:15:05.224
And then you would generate 4--

00:15:05.224 --> 00:15:06.390
yeah, that's right, just 4--

00:15:06.390 --> 00:15:08.890
I'm sorry, 4, 4
over here, if you

00:15:08.890 --> 00:15:10.660
want to call it an interval.

00:15:10.660 --> 00:15:12.670
You could represent
this differently.

00:15:12.670 --> 00:15:14.950
There's nothing that
stopping you in Python

00:15:14.950 --> 00:15:20.590
to have these slightly more
complicated representations

00:15:20.590 --> 00:15:23.434
where you just have
0 here as a number.

00:15:23.434 --> 00:15:24.850
And if it's just
a number, then it

00:15:24.850 --> 00:15:28.360
represents an
interval of length 1,

00:15:28.360 --> 00:15:31.090
but let's just be
uniform about this.

00:15:31.090 --> 00:15:33.160
Usually, when you
have special cases

00:15:33.160 --> 00:15:35.700
and if you do things
heterogeneously,

00:15:35.700 --> 00:15:37.550
then you have more
code to write.

00:15:37.550 --> 00:15:40.000
It might get more efficient,
but there's usually

00:15:40.000 --> 00:15:41.200
more code to write.

00:15:41.200 --> 00:15:42.850
So you do 4, 4 here.

00:15:42.850 --> 00:15:47.680
And then you'd go up, and
then you'd have 5 comma 6.

00:15:47.680 --> 00:15:50.500
And then you would do 7 comma--

00:15:50.500 --> 00:15:52.890
I'm sorry, 7 comma 9.

00:15:52.890 --> 00:15:55.030
So this is the first
time you actually

00:15:55.030 --> 00:15:59.590
have something interesting, in
the sense that the interval has

00:15:59.590 --> 00:16:02.230
a representation that only
has two numbers in it,

00:16:02.230 --> 00:16:05.620
whereas you actually have
three people in that interval.

00:16:05.620 --> 00:16:07.840
And obviously, this
could be arbitrarily

00:16:07.840 --> 00:16:13.470
large in the context of people
getting into a baseball game--

00:16:13.470 --> 00:16:18.640
and so 7 through 9 and then
finally here 10 through 10.

00:16:18.640 --> 00:16:21.744
And so now you go
ahead, and you count

00:16:21.744 --> 00:16:24.160
and you realize that there's
four intervals here and three

00:16:24.160 --> 00:16:25.270
intervals here.

00:16:25.270 --> 00:16:27.820
And then you say, I'm
going to go ahead and go

00:16:27.820 --> 00:16:33.640
with the backwards and asking
the people who are-- well,

00:16:33.640 --> 00:16:36.460
according to you-- backwards
to flip their caps so we're all

00:16:36.460 --> 00:16:36.960
good.

00:16:39.310 --> 00:16:44.710
So I'm going to show
you code that implements

00:16:44.710 --> 00:16:46.910
exactly this algorithm.

00:16:46.910 --> 00:16:50.050
And while you see
the code, I want

00:16:50.050 --> 00:16:52.540
you to think about
this harder question.

00:16:52.540 --> 00:16:55.690
This code is going to do
exactly what we describe.

00:16:55.690 --> 00:17:01.490
It's going to go compute
all of these things,

00:17:01.490 --> 00:17:04.770
and as you can
imagine, he's going

00:17:04.770 --> 00:17:07.200
to make a pass through
this entire Python

00:17:07.200 --> 00:17:13.230
list, this group of people,
this queue of people,

00:17:13.230 --> 00:17:15.210
and is going to do
this computation.

00:17:15.210 --> 00:17:19.380
Then it's going to say,
4 is greater than 3.

00:17:19.380 --> 00:17:23.970
And then it's going to go
through and start calling out

00:17:23.970 --> 00:17:26.400
commands for each of
the backward intervals.

00:17:26.400 --> 00:17:32.160
So in some sense, it's going to
make two passes over the list.

00:17:32.160 --> 00:17:35.340
So the first pass is to get
all of the intervals together.

00:17:35.340 --> 00:17:36.540
Then there's a check.

00:17:36.540 --> 00:17:38.040
And then the second
pass is to take

00:17:38.040 --> 00:17:41.880
those backward
intervals, in this case,

00:17:41.880 --> 00:17:43.650
and call out those commands.

00:17:43.650 --> 00:17:45.810
So that's what I
mean by two passes.

00:17:45.810 --> 00:17:47.379
Yeah, please.

00:17:47.379 --> 00:17:49.504
AUDIENCE: You don't
necessarily need to count them,

00:17:49.504 --> 00:17:56.240
the 4 and 3 because whichever
orientation interval comes

00:17:56.240 --> 00:17:57.450
second is always going--

00:17:57.450 --> 00:17:58.491
SRINI DEVADAS: Brilliant.

00:17:58.491 --> 00:18:01.180
Brilliant.

00:18:01.180 --> 00:18:03.250
So I was going to say--

00:18:03.250 --> 00:18:05.060
if you didn't
understand what Ganatra

00:18:05.060 --> 00:18:10.930
said, wonderful because then
you can think about the question

00:18:10.930 --> 00:18:15.250
I'm going to ask and
ignore what he said.

00:18:15.250 --> 00:18:20.360
And then we'll get to, I
guess, the more efficient code.

00:18:20.360 --> 00:18:24.610
But what I was going to ask was,
is there a way that I'm looking

00:18:24.610 --> 00:18:27.580
at this, and I'm just going--
and I'm going to just start

00:18:27.580 --> 00:18:29.830
calling out by--

00:18:29.830 --> 00:18:34.730
the moment I see that there's
an interval, the moment I see--

00:18:34.730 --> 00:18:36.100
this is an interval.

00:18:36.100 --> 00:18:40.000
And I'm going to make
a call with respect

00:18:40.000 --> 00:18:45.040
to whether I'm going to
call out a command or not.

00:18:45.040 --> 00:18:50.830
And I'm going to do this in
one pass through this array.

00:18:50.830 --> 00:18:53.410
I want to do this in one
pass through the array.

00:18:53.410 --> 00:18:58.750
I want to look at this, and I
say, I see the interval 0, 0.

00:18:58.750 --> 00:19:01.810
Is that going to
be something that I

00:19:01.810 --> 00:19:04.360
need to worry about in
terms of that person

00:19:04.360 --> 00:19:08.350
having to flip his cap?

00:19:08.350 --> 00:19:13.189
And then I see B, B. And I say,
oh, the interval is 1 comma 2.

00:19:13.189 --> 00:19:14.980
Is that something I'm
going to have to deal

00:19:14.980 --> 00:19:17.140
with in terms of a command?

00:19:17.140 --> 00:19:21.580
And so someone else
other than Ganatra,

00:19:21.580 --> 00:19:24.790
tell me if there's a
one-pass algorithm.

00:19:24.790 --> 00:19:30.040
And explain to me why you
can do this in one pass

00:19:30.040 --> 00:19:31.280
through the array.

00:19:31.280 --> 00:19:34.930
And just in terms of
code, I'll preview this.

00:19:34.930 --> 00:19:37.540
The first algorithm needs--

00:19:37.540 --> 00:19:40.060
according to my coding,
which, isn't great--

00:19:40.060 --> 00:19:41.600
26 lines of code.

00:19:41.600 --> 00:19:43.810
The second one needs
eight lines of code.

00:19:43.810 --> 00:19:45.520
So yeah, go ahead.

00:19:45.520 --> 00:19:48.732
AUDIENCE: So after you
see the first interval,

00:19:48.732 --> 00:19:50.890
you know that the second
interval at the very least

00:19:50.890 --> 00:19:54.620
is going to have the same number
of commands as the first one.

00:19:54.620 --> 00:19:56.750
So you might as well always
go with the second one.

00:19:56.750 --> 00:19:58.600
So once you've
identified what type

00:19:58.600 --> 00:20:01.900
the first interval is, you
iterate through the list

00:20:01.900 --> 00:20:03.020
seeing--

00:20:03.020 --> 00:20:05.695
and once you identify the
first and second intervals,

00:20:05.695 --> 00:20:08.750
you iterate through every
type of the second interval

00:20:08.750 --> 00:20:10.298
and do a command for that.

00:20:10.298 --> 00:20:11.290
SRINI DEVADAS: That's
absolutely right.

00:20:11.290 --> 00:20:11.890
What was your name?

00:20:11.890 --> 00:20:12.556
AUDIENCE: Kevin.

00:20:12.556 --> 00:20:13.470
SRINI DEVADAS: Kevin?

00:20:13.470 --> 00:20:15.130
So you had it right.

00:20:15.130 --> 00:20:17.500
And Kevin has it right, as well.

00:20:17.500 --> 00:20:21.220
So the observation
here is actually--

00:20:21.220 --> 00:20:23.740
it was said a little bit
differently by Kevin,

00:20:23.740 --> 00:20:26.290
but I'm going to say it
a little bit differently.

00:20:26.290 --> 00:20:31.030
The observation is
simply that if you

00:20:31.030 --> 00:20:36.860
look at the very
first orientation,

00:20:36.860 --> 00:20:41.500
the very first orientation
is something which,

00:20:41.500 --> 00:20:47.390
at best, is going to be a tie.

00:20:47.390 --> 00:20:53.450
So if you had it ending
with 10 people, 0 through 9,

00:20:53.450 --> 00:20:55.910
then the number of
forward intervals

00:20:55.910 --> 00:21:00.350
is the same as the number
of backwards intervals.

00:21:00.350 --> 00:21:03.020
And if you went here, obviously,
the number of forward intervals

00:21:03.020 --> 00:21:05.570
is greater than the number
of backwards intervals.

00:21:05.570 --> 00:21:10.956
So you really only have to look
at the first person in line not

00:21:10.956 --> 00:21:12.580
to determine the
intervals because when

00:21:12.580 --> 00:21:13.954
you see the first
person in line,

00:21:13.954 --> 00:21:16.115
you have no idea what
the intervals are

00:21:16.115 --> 00:21:18.129
that are coming after.

00:21:18.129 --> 00:21:19.670
You have to generate
those intervals,

00:21:19.670 --> 00:21:22.160
so you have to make your
pass through the array.

00:21:22.160 --> 00:21:25.040
But the first person
in line gives it away

00:21:25.040 --> 00:21:28.490
in terms of what
the final result is

00:21:28.490 --> 00:21:33.230
going to be with respect
to your decision as to what

00:21:33.230 --> 00:21:37.070
set of commands you're
going to call up.

00:21:37.070 --> 00:21:42.890
And so because this is an F, you
basically say, I'm going to go,

00:21:42.890 --> 00:21:49.400
and I'm going to make the people
with the B's flip their caps.

00:21:49.400 --> 00:21:59.090
And that's a small observation
in terms of its insight.

00:21:59.090 --> 00:22:02.150
But obviously, it's
potent, in the sense

00:22:02.150 --> 00:22:05.330
that it's going to give
you a one-pass algorithm

00:22:05.330 --> 00:22:06.560
versus a two-pass algorithm.

00:22:06.560 --> 00:22:08.600
And as I mentioned,
it's going to give you

00:22:08.600 --> 00:22:13.790
a substantial reduction in the
amount of code that you write.

00:22:13.790 --> 00:22:17.219
So I'm going to show
you a bunch of code now.

00:22:17.219 --> 00:22:19.010
So this is usually how
this is going to go,

00:22:19.010 --> 00:22:22.880
by the way, this entire class.

00:22:22.880 --> 00:22:25.850
And this is kind of
my way of teaching,

00:22:25.850 --> 00:22:28.340
at least this type of material
that's algorithmic and has

00:22:28.340 --> 00:22:30.330
data structures and so on.

00:22:30.330 --> 00:22:33.080
I like explaining to
people what they're

00:22:33.080 --> 00:22:36.500
going to see in the code without
having to deal with Python

00:22:36.500 --> 00:22:39.770
syntax and worrying about
whether it's while loops

00:22:39.770 --> 00:22:42.890
or for loops and things like
that and tuples or arrays

00:22:42.890 --> 00:22:43.970
and things like that.

00:22:43.970 --> 00:22:47.330
So let's get into that.

00:22:50.400 --> 00:22:53.530
I don't need this.

00:22:53.530 --> 00:22:55.900
Ah, good.

00:22:55.900 --> 00:23:00.270
So the naive algorithm first--

00:23:00.270 --> 00:23:04.560
so what you see
here is an input.

00:23:04.560 --> 00:23:09.310
So "caps" is simply an
input Python list that has,

00:23:09.310 --> 00:23:12.510
as you can see from our
examples, the F's and the B's.

00:23:12.510 --> 00:23:14.640
And so F is Forwards,
and B is Backwards.

00:23:14.640 --> 00:23:17.100
And there are a couple
of different Python lists

00:23:17.100 --> 00:23:19.400
so you can run them
with different things.

00:23:19.400 --> 00:23:22.200
And all of this hopefully is
not at all surprising to you

00:23:22.200 --> 00:23:23.670
because we went
through all of this

00:23:23.670 --> 00:23:25.860
in terms of the pseudocode.

00:23:25.860 --> 00:23:28.960
So the first initialization--

00:23:28.960 --> 00:23:31.980
and I can just highlight
that to make it easy.

00:23:31.980 --> 00:23:34.050
So that's initialization.

00:23:34.050 --> 00:23:35.910
And this part here--

00:23:35.910 --> 00:23:37.800
the comment sort
of gives it away--

00:23:37.800 --> 00:23:41.610
is you're making a
pass through the array,

00:23:41.610 --> 00:23:44.160
computing the intervals.

00:23:44.160 --> 00:23:47.620
And so how do you actually
get the intervals?

00:23:47.620 --> 00:23:52.240
And there's one line
of code that does that.

00:23:52.240 --> 00:23:54.750
And oh, by the way, if there
are any questions about Python

00:23:54.750 --> 00:23:57.590
syntax, just don't feel shy.

00:23:57.590 --> 00:24:00.180
Just tell me.

00:24:00.180 --> 00:24:02.890
Ask me a question, and
I'm happy to explain it.

00:24:02.890 --> 00:24:06.210
I don't want to explain things
that you all know, obviously.

00:24:06.210 --> 00:24:10.300
But if any one of you doesn't
know any particular thing,

00:24:10.300 --> 00:24:12.810
please don't feel shy.

00:24:12.810 --> 00:24:15.870
Syntax is something that
sometimes you even forget.

00:24:15.870 --> 00:24:17.460
I tend to forget things.

00:24:17.460 --> 00:24:21.210
So this thing here
is essentially

00:24:21.210 --> 00:24:26.400
something that decides on
what the intervals are.

00:24:26.400 --> 00:24:28.710
And the insight here is simple.

00:24:28.710 --> 00:24:32.370
You know that this interval
ended when you see something

00:24:32.370 --> 00:24:36.440
here that is different from
what the previous one is.

00:24:36.440 --> 00:24:37.440
So that's when you know.

00:24:37.440 --> 00:24:45.240
So you generate the interval
when you go and find

00:24:45.240 --> 00:24:49.530
something that is different
from the current location

00:24:49.530 --> 00:24:50.850
that you're pointing to.

00:24:50.850 --> 00:24:53.730
So that's really what's
going on out here.

00:24:53.730 --> 00:24:59.950
In this line, you say, you're
setting a "start" here.

00:24:59.950 --> 00:25:02.400
"Start" is your counter,
and remember, "start"

00:25:02.400 --> 00:25:04.860
is getting set again here.

00:25:04.860 --> 00:25:06.519
Initially, it was set to 0.

00:25:06.519 --> 00:25:09.060
And if you ever get to the point
where you're looking at "i,"

00:25:09.060 --> 00:25:10.643
it's the next thing
you're looking at,

00:25:10.643 --> 00:25:13.140
and if "caps start," which
is the start of the interval,

00:25:13.140 --> 00:25:15.570
is different from "i," it
meant that the interval that

00:25:15.570 --> 00:25:18.390
began with "start" ended.

00:25:18.390 --> 00:25:20.310
And so you
essentially say, well,

00:25:20.310 --> 00:25:23.751
that needs to end at i minus 1
because obviously, "caps start"

00:25:23.751 --> 00:25:25.000
is different from "caps size."

00:25:25.000 --> 00:25:27.990
So this is the end of
the interval right here.

00:25:27.990 --> 00:25:31.080
And this particular
thing, our interval,

00:25:31.080 --> 00:25:35.240
is something that includes
both these two numbers,

00:25:35.240 --> 00:25:36.510
so it's not exactly that.

00:25:36.510 --> 00:25:39.734
But it also includes--

00:25:39.734 --> 00:25:43.300
where did my chalk go?

00:25:43.300 --> 00:25:46.930
It also includes whether
this is an F or not.

00:25:46.930 --> 00:25:49.909
So each of these things has--

00:25:49.909 --> 00:25:52.200
I'm not going to write it
out for all of those things--

00:25:52.200 --> 00:25:57.270
but has the orientation
inside of it.

00:25:57.270 --> 00:25:59.370
So that's what
you have out here.

00:25:59.370 --> 00:26:01.810
That's why we have three
of these in this tuple.

00:26:01.810 --> 00:26:06.090
This is a tuple because it's
got round brackets around it.

00:26:06.090 --> 00:26:09.980
I could have made it
a list if I wanted.

00:26:09.980 --> 00:26:12.300
And so that's essentially
what we have here.

00:26:12.300 --> 00:26:15.420
And now, here's what happens.

00:26:15.420 --> 00:26:19.020
In this particular piece of
code, when you get to the end

00:26:19.020 --> 00:26:22.980
and you fall off the end--

00:26:22.980 --> 00:26:28.500
so if you just end, then
this code essentially

00:26:28.500 --> 00:26:32.940
skips over and doesn't actually
put in the last interval

00:26:32.940 --> 00:26:34.800
because you don't see something.

00:26:34.800 --> 00:26:37.920
When you come up here and
you're off the end of the array,

00:26:37.920 --> 00:26:40.320
you fall off the
edge of the array,

00:26:40.320 --> 00:26:44.310
you don't see a B that
is different from F.

00:26:44.310 --> 00:26:47.100
So if you just wrote that code--

00:26:47.100 --> 00:26:54.810
so it's something that
I'd say many people would

00:26:54.810 --> 00:26:56.830
have a quote, "bug,"
where they wouldn't

00:26:56.830 --> 00:27:01.500
add this part of the code here
because they didn't realize

00:27:01.500 --> 00:27:03.750
this particular
point that I made.

00:27:03.750 --> 00:27:07.830
And so that last interval
doesn't get added in.

00:27:07.830 --> 00:27:09.990
And so you have a
bit more code here

00:27:09.990 --> 00:27:13.470
that decides on
the last interval.

00:27:13.470 --> 00:27:19.330
And then you count, and then you
go ahead and call the commands.

00:27:19.330 --> 00:27:21.230
So this all looks good?

00:27:21.230 --> 00:27:23.220
Yeah, we're good with this?

00:27:23.220 --> 00:27:27.580
Is there a way that
I could somehow

00:27:27.580 --> 00:27:29.515
eliminate these four
lines of code which

00:27:29.515 --> 00:27:34.660
are a little bit annoying and
just do things in the array?

00:27:34.660 --> 00:27:37.180
How could I, with
a little trick,

00:27:37.180 --> 00:27:41.500
eliminate those
four lines of code?

00:27:41.500 --> 00:27:45.610
I might need a little bit more
in, quote, "pre-processing,"

00:27:45.610 --> 00:27:46.920
but how would I eliminate that?

00:27:51.560 --> 00:27:52.364
Someone else?

00:27:52.364 --> 00:27:53.030
I'll get to you.

00:27:53.030 --> 00:27:53.530
Yeah.

00:27:53.530 --> 00:27:55.011
Go ahead.

00:27:55.011 --> 00:27:56.970
AUDIENCE: One way is
you can check thoroughly

00:27:56.970 --> 00:27:59.260
you've reached the end of the--

00:27:59.260 --> 00:28:00.856
the forward is equal
to the backwards.

00:28:00.856 --> 00:28:02.070
SRINI DEVADAS: You could
have an extra check.

00:28:02.070 --> 00:28:02.380
What's your name?

00:28:02.380 --> 00:28:03.250
AUDIENCE: Kanishka.

00:28:03.250 --> 00:28:04.249
SRINI DEVADAS: Kanishka?

00:28:04.249 --> 00:28:10.306
So Kanishka says that before
you reach the end of the array

00:28:10.306 --> 00:28:11.930
or when you reach
the end of the array,

00:28:11.930 --> 00:28:15.591
you go ahead and do a check
that you've reached the end

00:28:15.591 --> 00:28:17.465
and generate the interval
inside of it, which

00:28:17.465 --> 00:28:21.830
is kind of like moving
this code inside of it.

00:28:21.830 --> 00:28:23.210
So that's reasonable.

00:28:23.210 --> 00:28:26.810
I'm not sure that's going to be
as good as the way that I want

00:28:26.810 --> 00:28:29.000
and which I coded.

00:28:29.000 --> 00:28:31.970
Think about pre-processing.

00:28:31.970 --> 00:28:33.783
Think about taking
the array-- yeah?

00:28:33.783 --> 00:28:37.010
AUDIENCE: I guess you could add
a wrong interval at the end.

00:28:37.010 --> 00:28:38.090
SRINI DEVADAS: You could
add on a wrong interval.

00:28:38.090 --> 00:28:38.881
What was your name?

00:28:38.881 --> 00:28:39.660
AUDIENCE: Kevin.

00:28:39.660 --> 00:28:40.800
SRINI DEVADAS: Kevin, too?

00:28:40.800 --> 00:28:44.090
Just how many Kevins
do we have here?

00:28:44.090 --> 00:28:47.650
So you could do this.

00:28:47.650 --> 00:28:51.960
So let me show you something
that's a little bit more--

00:28:51.960 --> 00:28:55.620
so that was 26 lines of code.

00:28:55.620 --> 00:28:57.330
And so this says--

00:28:57.330 --> 00:28:59.100
this is the line
that's interesting.

00:28:59.100 --> 00:29:03.780
So I had F and B, and so I
don't want to add F or B there.

00:29:03.780 --> 00:29:06.750
But what is convenient
to do, as it turns out,

00:29:06.750 --> 00:29:08.880
is to just have something
that essentially says,

00:29:08.880 --> 00:29:09.910
there's an ending point.

00:29:09.910 --> 00:29:14.160
So you have an explicit end
to the array that is actually

00:29:14.160 --> 00:29:17.640
not something that would crash
if you tried to access it.

00:29:17.640 --> 00:29:20.340
You had n people in line,
and now you have effectively

00:29:20.340 --> 00:29:21.720
n plus 1 people in line.

00:29:21.720 --> 00:29:25.300
But that n plus one
person is a dummy,

00:29:25.300 --> 00:29:27.660
or you can call them "end."

00:29:27.660 --> 00:29:30.600
And then if you do
that, then that's it.

00:29:30.600 --> 00:29:33.150
The previous code works.

00:29:33.150 --> 00:29:35.190
You can just remove
those four lines,

00:29:35.190 --> 00:29:39.510
and it'll all just work
because your F or your B

00:29:39.510 --> 00:29:41.430
is not equal to "end."

00:29:41.430 --> 00:29:45.240
So whatever you had at the end--

00:29:45.240 --> 00:29:46.440
I'm sorry.

00:29:46.440 --> 00:29:48.510
I'm overloading terms here.

00:29:48.510 --> 00:29:53.400
Whatever you had at
the last element--

00:29:53.400 --> 00:29:57.530
whether it was a B because
it ended here or F--

00:29:57.530 --> 00:30:00.150
when you equate that
to "end," you're

00:30:00.150 --> 00:30:02.440
going to get an inequality.

00:30:02.440 --> 00:30:05.340
And so that last
interval gets generated--

00:30:05.340 --> 00:30:06.810
so small optimization.

00:30:06.810 --> 00:30:10.380
Tony Hoare was a very
famous computer scientist--

00:30:10.380 --> 00:30:12.960
said that "inside
every program, there's

00:30:12.960 --> 00:30:15.860
a smaller program
waiting to get out."

00:30:15.860 --> 00:30:18.690
So this is kind of
one of the themes

00:30:18.690 --> 00:30:23.670
that I'd like to harp on in
this class, which is it's

00:30:23.670 --> 00:30:25.620
nice to write compact code.

00:30:25.620 --> 00:30:28.300
Usually, if you can
write compact code,

00:30:28.300 --> 00:30:29.502
there are fewer bugs in it.

00:30:29.502 --> 00:30:30.960
And you don't want
to go overboard.

00:30:30.960 --> 00:30:33.360
You don't want too
many subtleties,

00:30:33.360 --> 00:30:36.280
but it's nice to
write compact code.

00:30:36.280 --> 00:30:39.210
And so this is a little
bit more compact.

00:30:39.210 --> 00:30:45.000
And then finally, here's
the one-pass algorithm.

00:30:45.000 --> 00:30:49.240
So the whole thing, the
"pleaseConformonepass,"

00:30:49.240 --> 00:30:55.560
is the smarter algorithm
that essentially says,

00:30:55.560 --> 00:30:59.010
look, if I just look at
the very first thing,

00:30:59.010 --> 00:31:03.540
I'm going to be able to
skip that and then move on.

00:31:03.540 --> 00:31:07.230
So this is fairly complicated.

00:31:07.230 --> 00:31:09.030
You know the algorithm.

00:31:09.030 --> 00:31:11.890
Trying to map that to
this code is non-trivial,

00:31:11.890 --> 00:31:14.640
so we'll spend a
minute or two on it.

00:31:14.640 --> 00:31:21.570
But here's how this works.

00:31:21.570 --> 00:31:23.700
And by the way,
just to make sure--

00:31:28.480 --> 00:31:30.280
so I've repeated things here.

00:31:30.280 --> 00:31:34.950
So the optimized algorithm
for that particular example

00:31:34.950 --> 00:31:36.930
produced these first
three commands.

00:31:36.930 --> 00:31:40.320
And then the one-pass
algorithm produced

00:31:40.320 --> 00:31:42.090
exactly the same commands.

00:31:42.090 --> 00:31:44.765
So this is good to do.

00:31:44.765 --> 00:31:46.140
It's always nice
to have a couple

00:31:46.140 --> 00:31:48.780
of different ways
of solving a problem

00:31:48.780 --> 00:31:51.990
because then you
can verify things.

00:31:51.990 --> 00:31:55.980
Anyway, so this piece
of code is essentially

00:31:55.980 --> 00:32:01.020
something that does a similar
trick to what we had before,

00:32:01.020 --> 00:32:07.800
in terms of adding
to the original list,

00:32:07.800 --> 00:32:09.480
adding an element.

00:32:09.480 --> 00:32:11.700
But we're not using "end" here.

00:32:11.700 --> 00:32:14.719
We're actually
saying, what we want

00:32:14.719 --> 00:32:17.260
to do because we're going to go
ahead and skip this, anyway--

00:32:17.260 --> 00:32:19.160
we know we're going
to skip the F.

00:32:19.160 --> 00:32:25.020
So whatever that is, we could
just sort of add up here.

00:32:25.020 --> 00:32:29.560
And so that makes it easy.

00:32:29.560 --> 00:32:33.810
You don't have to worry about
what the actual characters are

00:32:33.810 --> 00:32:36.060
and cooking up this
"end," which is different

00:32:36.060 --> 00:32:38.910
from the F or the
B because hey, it's

00:32:38.910 --> 00:32:41.880
possible that people
might use whatever

00:32:41.880 --> 00:32:45.150
they want to represent a
forward cap or a backward cap.

00:32:45.150 --> 00:32:46.710
So this is very clean.

00:32:46.710 --> 00:32:48.840
You go ahead and put
exactly that over here.

00:32:48.840 --> 00:32:51.810
You know you're going to skip
that interval because you're

00:32:51.810 --> 00:32:56.880
going to skip the first
interval, effectively,

00:32:56.880 --> 00:33:01.050
because that is what the
algorithm allows you to do.

00:33:01.050 --> 00:33:06.690
And then this part here is
doing what we had before.

00:33:06.690 --> 00:33:08.510
We're not even
generating the intervals.

00:33:08.510 --> 00:33:11.340
We're just directly
making the commands.

00:33:11.340 --> 00:33:15.390
So there are no tuples
in terms of the tuples

00:33:15.390 --> 00:33:17.880
and the appending of the
intervals data structure

00:33:17.880 --> 00:33:18.450
that we had.

00:33:18.450 --> 00:33:20.040
It's all gone.

00:33:20.040 --> 00:33:23.760
I'm just going to go ahead
and fire off these commands.

00:33:23.760 --> 00:33:30.540
And those commands are
written in kind of a funny way

00:33:30.540 --> 00:33:35.070
because I'm going
to go ahead and if I

00:33:35.070 --> 00:33:36.450
wanted to print
these things out,

00:33:36.450 --> 00:33:38.520
you'd have to do this
in this funny way.

00:33:38.520 --> 00:33:40.960
If you're willing to wait
and collect up the intervals,

00:33:40.960 --> 00:33:42.390
you can certainly do that.

00:33:42.390 --> 00:33:45.270
But this is absolutely
the most compact code

00:33:45.270 --> 00:33:49.350
that I could think of,
and I'm printing a command

00:33:49.350 --> 00:33:51.510
in two different parts.

00:33:51.510 --> 00:33:54.270
I'm printing the first part
of the command that says,

00:33:54.270 --> 00:33:56.970
people in positions.

00:33:56.970 --> 00:34:00.450
And that's the start
of the interval "i,"

00:34:00.450 --> 00:34:02.710
and I'm just using
a Python construct.

00:34:02.710 --> 00:34:07.590
This "end" here is something
that the print command

00:34:07.590 --> 00:34:08.429
can recognize.

00:34:08.429 --> 00:34:10.560
And this simply says,
don't give me a new line.

00:34:10.560 --> 00:34:11.909
I want to print it exactly.

00:34:11.909 --> 00:34:14.130
As you saw from
when I ran the code,

00:34:14.130 --> 00:34:18.810
the printing was exactly the
same as the original algorithm.

00:34:18.810 --> 00:34:21.780
And so this "end" simply
says, don't print a new line

00:34:21.780 --> 00:34:24.590
at the end of
people in positions,

00:34:24.590 --> 00:34:25.650
whatever this number is.

00:34:25.650 --> 00:34:26.969
Call it 7.

00:34:26.969 --> 00:34:28.800
And you don't
print the new line.

00:34:28.800 --> 00:34:32.520
And then you have a space
here because you didn't

00:34:32.520 --> 00:34:34.770
print a new line or a space.

00:34:34.770 --> 00:34:37.770
And you go through i minus
1, which is exactly the same

00:34:37.770 --> 00:34:38.940
as we had before.

00:34:38.940 --> 00:34:42.449
You only discover that the
end of an interval after you

00:34:42.449 --> 00:34:46.889
see the person that
comes after the interval.

00:34:46.889 --> 00:34:48.909
So you have to go
back to i minus 1.

00:34:48.909 --> 00:34:50.790
So this makes sense?

00:34:50.790 --> 00:34:53.250
Any questions about this code?

00:34:53.250 --> 00:34:54.296
Yeah, go ahead.

00:34:54.296 --> 00:34:55.670
AUDIENCE: So the
first line, like

00:34:55.670 --> 00:34:57.980
you said, if we're going
to move the first--

00:34:57.980 --> 00:35:00.249
SRINI DEVADAS: Not
move, duplicate--

00:35:00.249 --> 00:35:01.540
AUDIENCE: Duplicate the first--

00:35:01.540 --> 00:35:02.373
SRINI DEVADAS: Yeah.

00:35:02.373 --> 00:35:05.030
So the plus there
is a concatenation,

00:35:05.030 --> 00:35:05.990
and you have two lists.

00:35:05.990 --> 00:35:07.310
"Caps" is a list.

00:35:07.310 --> 00:35:11.170
And when you use a plus
operator in Python,

00:35:11.170 --> 00:35:14.420
you can only add things
that are of the same type.

00:35:14.420 --> 00:35:17.990
And so "caps" is a
list, and "cap 0"

00:35:17.990 --> 00:35:19.710
is an element of the list.

00:35:19.710 --> 00:35:21.500
And so you need to
make it a list in order

00:35:21.500 --> 00:35:23.342
to use the plus operator.

00:35:23.342 --> 00:35:25.550
There are also other things
you could do using a pen,

00:35:25.550 --> 00:35:26.574
for example.

00:35:26.574 --> 00:35:28.990
So you could take that line,
and you could do "caps start"

00:35:28.990 --> 00:35:30.229
at "pen" "cap 0."

00:35:30.229 --> 00:35:32.270
And you wouldn't need all
of the square brackets,

00:35:32.270 --> 00:35:34.330
but that's just
neither here nor there.

00:35:34.330 --> 00:35:36.820
But I'm obviously not answering
your question, so go ahead.

00:35:36.820 --> 00:35:37.320
Yeah.

00:35:37.320 --> 00:35:39.248
AUDIENCE: So I was
going to say that we

00:35:39.248 --> 00:35:40.435
skip the first interval.

00:35:40.435 --> 00:35:43.134
And then we flip all the
second-type orientation.

00:35:43.134 --> 00:35:44.300
SRINI DEVADAS: That's right.

00:35:44.300 --> 00:35:46.210
AUDIENCE: But here, we're
focusing on the first element.

00:35:46.210 --> 00:35:46.710
Why--

00:35:49.190 --> 00:35:52.640
SRINI DEVADAS: Ah, but
that's OK because remember,

00:35:52.640 --> 00:35:57.830
the if statement is going
to skip this one, too.

00:35:57.830 --> 00:35:59.690
So if I had two F's
in the beginning--

00:35:59.690 --> 00:36:01.220
I think your question
is, what would

00:36:01.220 --> 00:36:04.905
happen if I had two F's or
three F's in the beginning?

00:36:04.905 --> 00:36:07.280
So I'm going to go ahead, and
first thing I'm going to do

00:36:07.280 --> 00:36:09.530
is I'm going to put
an F at the end here,

00:36:09.530 --> 00:36:11.310
and then maybe there's
a bunch of stuff.

00:36:11.310 --> 00:36:14.750
But then the nice thing is
that I'll skip this F, too,

00:36:14.750 --> 00:36:20.780
because the not equal
to is not going to fire.

00:36:20.780 --> 00:36:25.220
The next line, the "caps
i not equal to i minus 1,"

00:36:25.220 --> 00:36:27.512
this is going to be equal to.

00:36:27.512 --> 00:36:29.720
So I'm going to go ahead
and go to the next iteration

00:36:29.720 --> 00:36:30.770
of the loop.

00:36:30.770 --> 00:36:31.910
That makes sense?

00:36:31.910 --> 00:36:34.770
Did people understand
Fadi's question?

00:36:34.770 --> 00:36:36.740
It was a good question.

00:36:36.740 --> 00:36:41.630
So the question was, you
skipped the first one.

00:36:41.630 --> 00:36:43.970
But what is making you skip
this one because you want

00:36:43.970 --> 00:36:46.280
to skip the first interval?

00:36:46.280 --> 00:36:50.580
And so that if statement
is making you do that.

00:36:50.580 --> 00:36:51.080
Good.

00:36:51.080 --> 00:36:53.587
So as you can see, even a
fairly straightforward puzzle--

00:36:53.587 --> 00:36:55.670
this is the simplest puzzle
we're going to do here

00:36:55.670 --> 00:36:57.610
is the first one.

00:36:57.610 --> 00:37:01.830
And there are nuances
associated with how you solve it

00:37:01.830 --> 00:37:03.980
but also how you code it.

00:37:03.980 --> 00:37:06.080
And this is kind of--

00:37:06.080 --> 00:37:12.960
like I said, this was my
eureka moment a few years ago,

00:37:12.960 --> 00:37:15.380
where I said, I
think the way you

00:37:15.380 --> 00:37:17.790
want to teach
programming, at least

00:37:17.790 --> 00:37:21.560
some aspects of programming,
is in this fashion.

00:37:21.560 --> 00:37:22.550
Anyway, good.

00:37:22.550 --> 00:37:25.100
So we're done with this.

00:37:25.100 --> 00:37:27.540
Any questions about this puzzle?

00:37:27.540 --> 00:37:28.040
All right.

00:37:28.040 --> 00:37:29.590
Good.