Stay hungry. Stay foolish.

I am honored to be with you today for your commencement from one of the finest universities in the world. Truth be told, I never graduated from college. And this is the closest I’ve ever gotten to a college graduation. Today I want to tell you three stories from my life. That’s it. No big deal. Just three stories.

The first story is about connecting the dots.

I dropped out of Reed College after the first 6 months, but then stayed around as a drop-in for another 18 months or so before I really quit. So why did I drop out?

It started before I was born. My biological mother was a young, unwed graduate student, and she decided to put me up for adoption. She felt very strongly that I should be adopted by college graduates, so everything was all set for me to be adopted at birth by a lawyer and his wife. Except that when I popped out they decided at the last minute that they really wanted a girl. So my parents, who were on a waiting list, got a call in the middle of the night asking: “We have an unexpected baby boy; do you want him?” They said: “Of course.” My biological mother found out later that my mother had never graduated from college and that my father had never graduated from high school. She refused to sign the final adoption papers. She only relented a few months later when my parents promised that I would go to college. This was the start in my life.

And 17 years later I did go to college. But I naively chose a college that was almost as expensive as Stanford, and all of my working-class parents’ savings were being spent on my college tuition. After six months, I couldn”t see the value in it. I had no idea what I wanted to do with my life and no idea how college was going to help me figure it out. And here I was spending all of the money my parents had saved their entire life. So I decided to drop out and trust that it would all work out OK. It was pretty scary at the time, but looking back it was one of the best decisions I ever made. The minute I dropped out I could stop taking the required classes that didn’t interest me, and begin dropping in on the ones that looked interesting.

It wasn’t all romantic. I didn’t have a dorm room, so I slept on the floor in friends’ rooms, I returned Coke bottles for the 5¢ deposits to buy food with, and I would walk the 7 miles across town every Sunday night to get one good meal a week at the Hare Krishna temple. I loved it. And much of what I stumbled into by following my curiosity and intuition turned out to be priceless later on. Let me give you one example:

Reed College at that time offered perhaps the best calligraphy instruction in the country. Throughout the campus every poster, every label on every drawer, was beautifully hand calligraphed. Because I had dropped out and didn’t have to take the normal classes, I decided to take a calligraphy class to learn how to do this. I learned about serif and sans serif typefaces, about varying the amount of space between different letter combinations, about what makes great typography great. It was beautiful, historical, artistically subtle in a way that science can’t capture, and I found it fascinating.

None of this had even a hope of any practical application in my life. But 10 years later, when we were designing the first Macintosh computer, it all came back to me. And we designed it all into the Mac. It was the first computer with beautiful typography. If I had never dropped in on that single course in college, the Mac would have never had multiple typefaces or proportionally spaced fonts. And since Windows just copied the Mac, it’s likely that no personal computer would have them. If I had never dropped out, I would have never dropped in on this calligraphy class, and personal computers might not have the wonderful typography that they do. Of course it was impossible to connect the dots looking forward when I was in college. But it was very, very clear looking backward 10 years later.

Again, you can’t connect the dots looking forward; you can only connect them looking backward. So you have to trust that the dots will somehow connect in your future. You have to trust in something — your gut, destiny, life, karma, whatever. Beleiveing that the dots will connect down the road will give you the confidence to follow your heart, Even when it leads you off the well worn path, and that will make all the difference.

My second story is about love and loss.

I was lucky — I found what I loved to do early in life. Woz and I started Apple in my parents’ garage when I was 20. We worked hard, and in 10 years Apple had grown from just the two of us in a garage into a $2 billion company with over 4,000 employees. We had just released our finest creation — the Macintosh — a year earlier, and I had just turned 30. And then I got fired. How can you get fired from a company you started? Well, as Apple grew we hired someone who I thought was very talented to run the company with me, and for the first year or so things went well. But then our visions of the future began to diverge and eventually we had a falling out. When we did, our Board of Directors sided with him. So at 30 I was out. And very publicly out. What had been the focus of my entire adult life was gone, and it was devastating.

I really didn’t know what to do for a few months. I felt that I had let the previous generation of entrepreneurs down — that I had dropped the baton as it was being passed to me. I met with David Packard and Bob Noyce and tried to apologize for screwing up so badly. I was a very public failure, and I even thought about running away from the valley. But something slowly began to dawn on me — I still loved what I did. The turn of events at Apple had not changed that one bit. I had been rejected, but I was still in love. And so I decided to start over.

I didn’t see it then, but it turned out that getting fired from Apple was the best thing that could have ever happened to me. The heaviness of being successful was replaced by the lightness of being a beginner again, less sure about everything. It freed me to enter one of the most creative periods of my life.

During the next five years, I started a company named NeXT, another company named Pixar, and fell in love with an amazing woman who would become my wife. Pixar went on to create the world’s first computer animated feature film, Toy Story, and is now the most successful animation studio in the world. In a remarkable turn of events, Apple bought NeXT, I returned to Apple, and the technology we developed at NeXT is at the heart of Apple’s current renaissance. And Laurene and I have a wonderful family together.

I’m pretty sure none of this would have happened if I hadn’t been fired from Apple. It was awful tasting medicine, but I guess the patient needed it. Sometimes life hits you in the head with a brick. Don’t lose faith. I’m convinced that the only thing that kept me going was that I loved what I did. You’ve got to find what you love. And that is as true for your work as it is for your lovers. Your work is going to fill a large part of your life, and the only way to be truly satisfied is to do what you believe is great work. And the only way to do great work is to love what you do. If you haven’t found it yet, keep looking. Don’t settle. As with all matters of the heart, you’ll know when you find it. And, like any great relationship, it just gets better and better as the years roll on. So keep looking until you find it. Don’t settle.

My third story is about death.

When I was 17, I read a quote that went something like: “If you live each day as if it was your last, someday you’ll most certainly be right.” It made an impression on me, and since then, for the past 33 years, I have looked in the mirror every morning and asked myself: “**If today were the last day of my life, would I want to do what I am about to do today?**” And whenever the answer has been “No” for too many days in a row, I know I need to change something.

Remembering that I’ll be dead soon is the most important tool I’ve ever encountered to help me make the big choices in life. Because almost everything — all external expectations, all pride, all fear of embarrassment or failure — these things just fall away in the face of death, leaving only what is truly important. Remembering that you are going to die is the best way I know to avoid the trap of thinking you have something to lose. You are already naked. There is no reason not to follow your heart.

About a year ago I was diagnosed with cancer. I had a scan at 7:30 in the morning, and it clearly showed a tumor on my pancreas. I didn’t even know what a pancreas was. The doctors told me this was almost certainly a type of cancer that is incurable, and that I should expect to live no longer than three to six months. My doctor advised me to go home and get my affairs in order, which is doctor’s code for prepare to die. It means to try to tell your kids everything you thought you’d have the next 10 years to tell them in just a few months. It means to make sure everything is buttoned up so that it will be as easy as possible for your family. It means to say your goodbyes.

I lived with that diagnosis all day. Later that evening I had a biopsy, where they stuck an endoscope down my throat, through my stomach and into my intestines, put a needle into my pancreas and got a few cells from the tumor. I was sedated, but my wife, who was there, told me that when they viewed the cells under a microscope the doctors started crying because it turned out to be a very rare form of pancreatic cancer that is curable with surgery. I had the surgery and thankfully I’m fine now.

This was the closest I’ve been to facing death, and I hope it’s the closest I get for a few more decades. Having lived through it, I can now say this to you with a bit more certainty than when death was a useful but purely intellectual concept:

No one wants to die. Even people who want to go to heaven don’t want to die to get there. And yet death is the destination we all share. No one has ever escaped it. And that is as it should be, because Death is very likely the single best invention of Life. It is Life’s change agent. It clears out the old to make way for the new. Right now the new is you, but someday not too long from now, you will gradually become the old and be cleared away. Sorry to be so dramatic, but it is quite true.

Your time is limited, so don’t waste it living someone else’s life. Don’t be trapped by dogma — which is living with the results of other people’s thinking. Don’t let the noise of others’ opinions drown out your own inner voice. And most important, have the courage to follow your heart and intuition. They somehow already know what you truly want to become. Everything else is secondary.

When I was young, there was an amazing publication called The Whole Earth Catalog, which was one of the bibles of my generation. It was created by a fellow named Stewart Brand not far from here in Menlo Park, and he brought it to life with his poetic touch. This was in the late 1960s, before personal computers and desktop publishing, so it was all made with typewriters, scissors and polaroid cameras. It was sort of like Google in paperback form, 35 years before Google came along: It was idealistic, and overflowing with neat tools and great notions.

Stewart and his team put out several issues of The Whole Earth Catalog, and then when it had run its course, they put out a final issue. It was the mid-1970s, and I was your age. On the back cover of their final issue was a photograph of an early morning country road, the kind you might find yourself hitchhiking on if you were so adventurous. Beneath it were the words: “**Stay Hungry. Stay Foolish.**” It was their farewell message as they signed off. Stay Hungry. Stay Foolish. And I have always wished that for myself. And now, as you graduate to begin anew, I wish that for you.

Stay Hungry. Stay Foolish.

Thank you all very much.


How to Grow Old

by Bertrand Russell

In spite of the title, this article will really be on how not to grow old, which, at my time of life, is a much more important subject. My first advice would be to choose your ancestors carefully. Although both my parents died young, I have done well in this respect as regards my other ancestors. My maternal grandfather, it is true, was cut off in the flower of his youth at the age of sixty-seven, but my other three grandparents all lived to be over eighty. Of remoter ancestors I can only discover one who did not live to a great age, and he died of a disease which is now rare, namely, having his head cut off. A great-grandmother of mine, who was a friend of Gibbon, lived to the age of ninety-two, and to her last day remained a terror to all her descendants. My maternal grandmother, after having nine children who survived, one who died in infancy, and many miscarriages, as soon as she became a widow devoted herself to women’s higher education. She was one of the founders of Girton College, and worked hard at opening the medical profession to women. She used to tell of how she met in Italy an elderly gentleman who was looking very sad. She asked him why he was so melancholy and he said that he had just parted from his two grandchildren. ‘Good gracious,’ she exclaimed, ‘I have seventy-two grandchildren, and if I were sad each time I parted from one of them, I should have a miserable existence!’ ‘Madre snaturale!,’ he replied. But speaking as one of the seventy-two, I prefer her recipe. After the age of eighty she found she had some difficulty in getting to sleep, so she habitually spent the hours from midnight to 3 a.m. in reading popular science. I do not believe that she ever had time to notice that she was growing old. This, I think, is the proper recipe for remaining young. If you have wide and keen interests and activities in which you can still be effective, you will have no reason to think about the merely statistical fact of the number of years you have already lived, still less of the probable shortness of your future.

As regards health, I have nothing useful to say as I have little experience of illness. I eat and drink whatever I like, and sleep when I cannot keep awake. I never do anything whatever on the ground that it is good for health, though in actual fact the things I like doing are mostly wholesome.

Psychologically there are two dangers to be guarded against in old age. One of these is undue absorption in the past. It does not do to live in memories, in regrets for the good old days, or in sadness about friends who are dead. One’s thoughts must be directed to the future, and to things about which there is something to be done. This is not always easy; one’s own past is a gradually increasing weight. It is easy to think to oneself that one’s emotions used to be more vivid than they are, and one’s mind more keen. If this is true it should be forgotten, and if it is forgotten it will probably not be true.

The other thing to be avoided is clinging to youth in the hope of sucking vigour from its vitality. When your children are grown up they want to live their own lives, and if you continue to be as interested in them as you were when they were young, you are likely to become a burden to them, unless they are unusually callous. I do not mean that one should be without interest in them, but one’s interest should be contemplative and, if possible, philanthropic, but not unduly emotional. Animals become indifferent to their young as soon as their young can look after themselves, but human beings, owing to the length of infancy, find this difficult.

I think that a successful old age is easiest for those who have strong impersonal interests involving appropriate activities. It is in this sphere that long experience is really fruitful, and it is in this sphere that the wisdom born of experience can be exercised without being oppressive. It is no use telling grownup children not to make mistakes, both because they will not believe you, and because mistakes are an essential part of education. But if you are one of those who are incapable of impersonal interests, you may find that your life will be empty unless you concern yourself with your children and grandchildren. In that case you must realise that while you can still render them material services, such as making them an allowance or knitting them jumpers, you must not expect that they will enjoy your company.

Some old people are oppressed by the fear of death. In the young there is a justification for this feeling. Young men who have reason to fear that they will be killed in battle may justifiably feel bitter in the thought that they have been cheated of the best things that life has to offer. But in an old man who has known human joys and sorrows, and has achieved whatever work it was in him to do, the fear of death is somewhat abject and ignoble. The best way to overcome it - so at least it seems to me - is to make your interests gradually wider and more impersonal, until bit by bit the walls of the ego recede, and your life becomes increasingly merged in the universal life. An individual human existence should be like a river: small at first, narrowly contained within its banks, and rushing passionately past rocks and over waterfalls. Gradually the river grows wider, the banks recede, the waters flow more quietly, and in the end, without any visible break, they become merged in the sea, and painlessly lose their individual being. The man who, in old age, can see his life in this way, will not suffer from the fear of death, since the things he cares for will continue. And if, with the decay of vitality, weariness increases, the thought of rest will not be unwelcome. I should wish to die while still at work, knowing that others will carry on what I can no longer do and content in the thought that what was possible has been done.


Portraits from Memory


The last paragraph was selected as Lesson 11 How to grow old in New Concept English Book 4: Fluency in English by Louis George Alexander

What, according to the author, is the best way to overcome the fear of death as you get older?

The Work of Happiness

by May Sarton

I thought of happiness, how it is woven
Out of the silence in the empty house each day
And how it is not sudden and it is not given
But is creation itself like the growth of a tree.
No one has seen it happen, but inside the bark
Another circle is growing in the expanding ring.
No one has heard the root go deeper in the dark,
But the tree is lifted by this inward work
And its plumes shine, and its leaves are glittering.

So happiness is woven out of the peace of hours
And strikes its roots deep in the house alone:
The old chest in the corner, cool waxed floors,
White curtains softly and continually blown
As the free air moves quietly about the room;
A shelf of books, a table, and the white-washed wall—
These are the dear familiar gods of home,
And here the work of faith can best be done,
The growing tree is green and musical.

For what is happiness but growth in peace,
The timeless sense of time when furniture
Has stood a life’s span in a single place,
And as the air moves, so the old dreams stir
The shining leaves of present happiness?
No one has heard thought or listened to a mind,
But where people have lived in inwardness
The air is charged with blessing and does bless;
Windows look out on mountains and the walls are kind.


May Sarton, “The Work of Happiness” from Collected Poems 1930-1993. Copyright © 1993 by May Sarton.

Source: Collected Poems 1930-1993 (W. W. Norton & Company, Inc., 1993)


LeetCode - Algorithms - 1185. Day of the Week

Problem

1185. Day of the Week

Java

Doomsday Algorithm

The algorithm was devised by John Conway in 1973. It is simple enough that it can be computed mentally. Conway could usually give the correct answer in under two seconds.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
class Solution {
public String dayOfTheWeek(int day, int month, int year) {
String s = "";
int t[] = {0, 3, 2, 5, 0, 3, 5, 1, 4, 6, 2, 4};
if (month < 3) year -= 1;
int i = (year + year/4 - year/100 + year/400 + t[month-1] + day) % 7;
switch (i) {
case 1: s = "Monday"; break;
case 2: s = "Tuesday"; break;
case 3: s = "Wednesday"; break;
case 4: s = "Thursday"; break;
case 5: s = "Friday"; break;
case 6: s = "Saturday"; break;
case 0: case 7: s = "Sunday"; break;
default: ;
}

return s;
}
}

Submission Detail

  • 39 / 39 test cases passed.
  • Runtime: 0 ms, faster than 100.00% of Java online submissions for Day of the Week.
  • Memory Usage: 37 MB, less than 100.00% of Java online submissions for Day of the Week.

jdk8

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import java.time.LocalDate;

class Solution {
public String dayOfTheWeek(int day, int month, int year) {
String s = "";
LocalDate d = LocalDate.of(year, month, day);
switch (d.getDayOfWeek().getValue()) {
case 1: s = "Monday"; break;
case 2: s = "Tuesday"; break;
case 3: s = "Wednesday"; break;
case 4: s = "Thursday"; break;
case 5: s = "Friday"; break;
case 6: s = "Saturday"; break;
case 7: s = "Sunday"; break;
default: ;
}
return s;
}
}

Submission Detail

  • 39 / 39 test cases passed.
  • Runtime: 1 ms, faster than 26.65% of Java online submissions for Day of the Week.
  • Memory Usage: 37.2 MB, less than 100.00% of Java online submissions for Day of the Week.

Resources

Classical Music

by Sharon Wiseman

Classical music makes me cry
Each time I hear a piece
My heart wells up with so much joy
Until music cease Chopin, Beethoven, and Mozart too
Make the inner sole want to sing
It makes me happy to hear the notes
To each note my heart wants to cling Classical music has never meant so much
To me until to Europe I went
But now it brings overwhelming joy
Many hours of listening are spent What a wondrous talent the writers did have
Of the Classicals I listen to each day
The joy it brings to many of us
Will last forever each day that it’s played.

LeetCode - Algorithms - 912. Sort an Array

Problem

Given an array of integers nums, sort the array in ascending order.

912. Sort an Array

Java

Insertion sort

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
class Solution {
public int[] sortArray(int[] nums) {
int temp;
for (int i = 1; i < nums.length; i++) {
for (int j = i; j > 0; j--) {
if (nums[j] < nums[j - 1]) {
temp = nums[j];
nums[j] = nums[j-1];
nums[j-1] = temp;
}
}
}
return nums;
}
}

Submission Detail

  • 10 / 10 test cases passed.
  • Runtime: 1323 ms, faster than 5.01% of Java online submissions for Sort an Array.
  • Memory Usage: 47.2 MB, less than 6.12% of Java online submissions for Sort an Array.

Mergesort

bottom-up mergesort

This method requires even less code than the standard recursive implementation.

© Robert Sedgewick and Kevin Wayne

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
class Solution {
private void merge(int[] a, int[] aux, int lo, int mid, int hi) {
// copy to aux[]
for (int k = lo; k <= hi; k++) {
aux[k] = a[k];
}

// merge back to a[]
int i = lo, j = mid + 1;
for (int k = lo; k <= hi; k++) {
if (i > mid) a[k] = aux[j++];
else if (j > hi) a[k] = aux[i++];
else if (aux[j] < aux[i]) a[k] = aux[j++];
else a[k] = aux[i++];
}
}

public int[] sortArray(int[] nums) {
final int N = nums.length;
int[] aux = new int[N];
for (int len = 1; len < N; len *= 2) {
for (int lo = 0; lo < N - len; lo += len + len) {
int mid = lo + len - 1;
int hi = Math.min(lo + len + len - 1, N - 1);
merge(nums, aux, lo, mid, hi);
}
}
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 7 ms, faster than 34.85% of Java online submissions for Sort an Array.
  • Memory Usage: 46.7 MB, less than 12.67% of Java online submissions for Sort an Array.

Top-down mergesort

recursive method

© Robert Sedgewick and Kevin Wayne

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
class Solution {
private void merge(int[] a, int[] aux, int lo, int mid, int hi) {
// copy to aux[]
for (int k = lo; k <= hi; k++) {
aux[k] = a[k];
}

// merge back to a[]
int i = lo, j = mid + 1;
for (int k = lo; k <= hi; k++) {
if (i > mid) a[k] = aux[j++];
else if (j > hi) a[k] = aux[i++];
else if (aux[j] < aux[i]) a[k] = aux[j++];
else a[k] = aux[i++];
}
}

private void sort(int[] a, int[] aux, int lo, int hi) {
if (hi <= lo) return;
int mid = lo + (hi - lo) / 2;
sort(a, aux, lo, mid);
sort(a, aux, mid + 1, hi);
merge(a, aux, lo, mid, hi);
}

public int[] sortArray(int[] nums) {
final int N = nums.length;
int[] aux = new int[N];
sort(nums, aux, 0, N - 1);
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 6 ms, faster than 57.85% of Java online submissions for Sort an Array.
  • Memory Usage: 46.3 MB, less than 14.62% of Java online submissions for Sort an Array.

Shellsort

© Robert Sedgewick and Kevin Wayne

Example of simple idea leading to substantial performance gains.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
class Solution {
public int[] sortArray(int[] nums) {
final int N = nums.length;
int h = 1;
for (; h < N / 3; h = 3 * h + 1) ;
int temp;
for (; h >= 1; h /= 3) {
for (int i = h; i < N; i++) {
for (int j = i; j >= h; j -= h) {
if (nums[j] < nums[j - h]) {
temp = nums[j];
nums[j] = nums[j - h];
nums[j - h] = temp;
}
}
}
}
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 1865 ms, faster than 5.04% of Java online submissions for Sort an Array.
  • Memory Usage: 46.2 MB, less than 18.92% of Java online submissions for Sort an Array.

Quicksort

1

© John Bentley, Programming Pearls

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
class Solution {
public int[] sortArray(int[] nums) {
qsort(0,nums.length-1, nums);
return nums;
}

/**
* Quicksort
* Programming Pearls
* @author John Bentley
* @param l
* @param u
* @param inArr
*/
private void qsort(int l, int u, int[] inArr) {
if (l>=u) return;
int m=l;
for(int i=l+1;i<=u; i++)
if (inArr[i]<inArr[l])
swap(inArr, ++m, i);
swap(inArr, l, m);
qsort(l,m-1,inArr);
qsort(m+1,u,inArr);
}

private void swap(int[] arr, int i, int j) {
int temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}

Submission Detail

  • 10 / 10 test cases passed.
  • Runtime: 4 ms, faster than 91.33% of Java online submissions for Sort an Array.
  • Memory Usage: 46.8 MB, less than 6.12% of Java online submissions for Sort an Array.

quicksort with 3-way partitioning

© Robert Sedgewick and Kevin Wayne

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class Solution {
private void exch(int[] a, int i, int j) {
int swap = a[i];
a[i] = a[j];
a[j] = swap;
}

private void sort(int[] a, int lo, int hi) {
if (hi <= lo) return;
int lt = lo, gt = hi;
int v = a[lo];
int i = lo + 1;
while (i <= gt) {
if (a[i] < v) exch(a, lt++, i++);
else if (a[i] > v) exch(a, i, gt--);
else i++;
}

// a[lo..lt-1] < v = a[lt..gt] < a[gt+1..hi].
sort(a, lo, lt - 1);
sort(a, gt + 1, hi);
}

public int[] sortArray(int[] nums) {
final int N = nums.length;
sort(nums, 0, N - 1);
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 4 ms, faster than 89.87% of Java online submissions for Sort an Array.
  • Memory Usage: 46.9 MB, less than 12.99% of Java online submissions for Sort an Array.

selection sort

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
class Solution {
public int[] sortArray(int[] nums) {
final int N = nums.length;
int temp;
for (int i = 0; i < N; i++) {
int min = i;
for (int j = i + 1; j < N; j++) {
if (nums[j] < nums[min])
min = j;
}
temp = nums[min];
nums[min] = nums[i];
nums[i] = temp;
}
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 1169 ms, faster than 5.10% of Java online submissions for Sort an Array.
  • Memory Usage: 46.3 MB, less than 86.77% of Java online submissions for Sort an Array.

heap sort

iterative

© Robert Sedgewick and Kevin Wayne

Heapsort breaks into two phases: heap construction, where we reorganize the original array into a heap, and the sortdown, where we pull the items out of the heap in decreasing order to build the sorted result.

Q. Why not use a[0] in the heap representation?

A. Doing so simplifies the arithmetic a bit. It is not difficult to implement the heap methods based on a 0-based heap where the children of a[0] are a[1] and a[2], the children of a[1] are a[3] and a[4], the children of a[2] are a[5] and a[6], and so forth, but most programmers prefer the simpler arithmetic that we use. Also, using a[0] as a sentinel value (in the parent of a[1]) is useful in some heap applications.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
class Solution {
private void exch(int[] a, int i, int j) {
int swap = a[i];
a[i] = a[j];
a[j] = swap;
}

private void sink(int[] pq, int k, int n) {
while (2 * k <= (n - 1)) {
int j = 2 * k;
if (j < (n - 1) && pq[j] < pq[j + 1]) j++;
if (!(pq[k] < pq[j])) break;
exch(pq, k, j);
k = j;
}
}

public int[] sortArray(int[] nums) {
int n = nums.length;
for (int k = (n - 1) / 2; k >= 0; k--)
sink(nums, k, n);
for (int k = n - 1; k > 0; k--) {
exch(nums, 0, k);
sink(nums, 0, k);
}
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 6 ms, faster than 53.50% of Java online submissions for Sort an Array.
  • Memory Usage: 46.6 MB, less than 48.27% of Java online submissions for Sort an Array.

recursion

© HeapSort

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
class Solution {
private void exch(int[] a, int i, int j) {
int swap = a[i];
a[i] = a[j];
a[j] = swap;
}

private void sink(int[] pq, int k, int n) {
int largest = k;
int l = 2 * k + 1;
int r = 2 * k + 2;
if (l < n && pq[l] > pq[largest])
largest = l;
if (r < n && pq[r] > pq[largest])
largest = r;
if (largest != k) {
exch(pq, k, largest);
sink(pq, largest, n);
}
}

public int[] sortArray(int[] nums) {
int n = nums.length;
for (int k = n / 2 - 1; k >= 0; k--)
sink(nums, k, n);
for (int k = n - 1; k > 0; k--) {
exch(nums, 0, k);
sink(nums, 0, k);
}
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 7 ms, faster than 30.29% of Java online submissions for Sort an Array.
  • Memory Usage: 46.7 MB, less than 32.93% of Java online submissions for Sort an Array.

jdk PriorityQueue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import java.util.PriorityQueue;
import java.util.Queue;

class Solution {
public int[] sortArray(int[] nums) {
Queue<Integer> q = new PriorityQueue<Integer>();
for (int num : nums) {
q.add(num);
}
int i = 0;
while (q.size() > 0)
nums[i++] = q.poll();
return nums;
}
}

Submission Detail

  • 11 / 11 test cases passed.
  • Runtime: 18 ms, faster than 16.69% of Java online submissions for Sort an Array.
  • Memory Usage: 47.7 MB, less than 11.36% of Java online submissions for Sort an Array.

LeetCode - Algorithms - 547. Friend Circles

Problem

547. Friend Circles

Java

union–find

© 1.5 Case Study: Union-Find Copyright © 2000–2019 Robert Sedgewick and Kevin Wayne. All rights reserved.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
class Solution {
public int findCircleNum(int[][] M) {
int N = M.length;
UF uf = new UF(N);
for(int i=0; i<N; i++) {
for(int j=0; j<i; j++) {
if (M[i][j]==1)
uf.union(i,j);
}
}
return uf.count();
}
}

/**
* Weighted quick-union by rank with path compression by halving.
* @author Robert Sedgewick
* @author Kevin Wayne
* Algorithms, 4th edition textbook code and libraries
* https://github.com/kevin-wayne/algs4
*/
class UF {
private int[] parent;
private byte[] rank;
private int count;

public UF(int n) {
if (n < 0) throw new IllegalArgumentException();
count = n;
parent = new int[n];
rank = new byte[n];
for (int i = 0; i < n; i++) {
parent[i] = i;
rank[i] = 0;
}
}

public int find(int p) {
validate(p);
while (p != parent[p]) {
parent[p] = parent[parent[p]];
p = parent[p];
}
return p;
}

public int count() {
return count;
}

public void union(int p, int q) {
int rootP = find(p);
int rootQ = find(q);
if (rootP == rootQ) return;

if (rank[rootP] < rank[rootQ]) parent[rootP] = rootQ;
else if (rank[rootP] > rank[rootQ]) parent[rootQ] = rootP;
else {
parent[rootQ] = rootP;
rank[rootP]++;
}
count--;
}

private void validate(int p) {
int n = parent.length;
if (p < 0 || p >= n) {
throw new IllegalArgumentException("index " + p + " is not between 0 and " + (n-1));
}
}
}

Submission Detail

  • 113 / 113 test cases passed.
  • Runtime: 1 ms, faster than 72.63% of Java online submissions for Friend Circles.
  • Memory Usage: 40.3 MB, less than 68.00% of Java online submissions for Friend Circles.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
class Solution {
public int findCircleNum(int[][] M) {
int N = M.length;
List<Edge> edges = new ArrayList<Edge>();
for(int i=0; i<N; i++) {
for(int j=0; j<i; j++) {
if (M[i][j]==1) {
edges.add( new Edge(i,j) );
edges.add( new Edge(j,i) );
}
}
}
Graph graph = new Graph(edges, N);
boolean[] visited = new boolean[N];
for(int i=0; i<N; i++)
visited[i] = false;
int c = 0;
for(int i=0; i<N; i++) {
if (!visited[i]) {
dfs(graph, i, visited);
c++;
}
}

return c;
}

private void dfs(Graph graph, int v, boolean[] visited) {
visited[v] = true;
for (int u : graph.adjList.get(v)) {
if (!visited[u])
dfs(graph, u, visited);
}
}
}

class Edge {
int source, dest;

public Edge(int source, int dest) {
this.source = source;
this.dest = dest;
}
}

class Graph {
List<List<Integer>> adjList = null;

Graph(List<Edge> edges, int N) {
adjList = new ArrayList<>(N);

for (int i = 0; i < N; i++) {
adjList.add(i, new ArrayList<>());
}

for (Edge edge : edges) {
adjList.get(edge.source).add(edge.dest);
}
}
}

Submission Detail

  • 113 / 113 test cases passed.
  • Runtime: 4 ms, faster than 25.38% of Java online submissions for Friend Circles.
  • Memory Usage: 40.1 MB, less than 72.00% of Java online submissions for Friend Circles.

Resources

LeetCode - Algorithms - 867. Transpose Matrix

Problem

867. Transpose Matrix

Given a matrix A, return the transpose of A.

\( \begin{bmatrix}
1 &2 &3 \\
4 &5 &6 \\
7 &8 &9
\end{bmatrix} \Rightarrow \begin{bmatrix}
1 &4 &7 \\
2 &5 &8 \\
3 &6 &9
\end{bmatrix} \)

Java

1
2
3
4
5
6
7
8
9
10
11
12
class Solution {
public int[][] transpose(int[][] A) {
int h = A.length;
int w = A[0].length;
int[][] B = new int[w][h];
for(int i=0; i<h; i++) {
for(int j=0; j<w; j++)
B[j][i]=A[i][j];
}
return B;
}
}

Submission Detail

  • 36 / 36 test cases passed.
  • Runtime: 0 ms, faster than 100.00% of Java online submissions for Transpose Matrix.
  • Memory Usage: 40.6 MB, less than 91.67% of Java online submissions for Transpose Matrix.

A Response to "Bell's Conjecture"

\(\huge e^{i\pi}+1=0 \)

by Charlie Marion and William Dunham

Before we let you get away,
Your choices set in stone,
Consider what we have to say:
E.T.! O, please! Call home!

Stop the presses! Hold that thought!
And listen to our voices.
Ruffled, even overwrought,
We’ll supplement your choices.

Old Archie, Isaac, C. F. Gauss–
Though each deserves a floor
In mathematics’ honored house,
Make room for just one more.

Without the Bard of Basel, Bell,
You’ve clearly dropped the ball.
Our votes are cast for Euler, L.
Whose OPERA says it all:

Six dozen volumes — what a feat!
Profound and deep throughout
Does Leonhard rank with the elite?
Of this there is no doubt.

Consider how he summed, in turn
The quite elusive mix
Of one slash n all squared — you’ll learn
he got π2 slash six.

\( \zeta(2)=\sum_{n=1}^{\infty}\frac{1}{n^2} = \lim_{n \to \infty} (\frac{1}{1^2}+\frac{1}{2^2}+\frac{1}{3^2}+\cdots+\frac{1}{n^2}) = \frac{\pi^2}{6} \)

We’re shocked we did not see his name
With those you justly sainted.
No Euler in your Hall of Fame?
Your judgment’s surely Taine-ted.

It’s time to honor one you missed,
To do your duty well.
Add worthy Euler to your list,
And save him by the Bell.