<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom"><title>mx's blog - algorithm</title><link href="https://x-wei.github.io/" rel="alternate"/><link href="https://x-wei.github.io/feeds/tag-algorithm.atom.xml" rel="self"/><id>https://x-wei.github.io/</id><updated>2016-05-27T18:00:00+02:00</updated><entry><title>codejam常用(python)解题工具</title><link href="https://x-wei.github.io/tech/codejam-python-tools.html" rel="alternate"/><published>2016-05-27T18:00:00+02:00</published><updated>2016-05-27T18:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-05-27:/tech/codejam-python-tools.html</id><summary type="html">&lt;p&gt;总结一下用python撸codejam时常用的一些库, 并且给一些简单的例子. 发现用python撸codejam非常合适: codejam的时间要求不严格(4/8分钟), 而且程序只要本地运行. 正好可以使用python简洁的语法和丰富的函数库.    &lt;/p&gt;
&lt;h1 id="collections"&gt;collections&lt;/h1&gt;
&lt;p&gt;py自带的一些好用的数据结构...&lt;br/&gt;
&lt;a href="https://docs.python.org/2/library/collections.html"&gt;https://docs.python.org/2/library/collections.html …&lt;/a&gt;&lt;/p&gt;</summary><content type="html">&lt;p&gt;总结一下用python撸codejam时常用的一些库, 并且给一些简单的例子. 发现用python撸codejam非常合适: codejam的时间要求不严格(4/8分钟), 而且程序只要本地运行. 正好可以使用python简洁的语法和丰富的函数库.    &lt;/p&gt;
&lt;h1 id="collections"&gt;collections&lt;/h1&gt;
&lt;p&gt;py自带的一些好用的数据结构...&lt;br/&gt;
&lt;a href="https://docs.python.org/2/library/collections.html"&gt;https://docs.python.org/2/library/collections.html&lt;/a&gt; &lt;/p&gt;
&lt;p&gt;&lt;code&gt;from collections import Counter, deque, defaultdict&lt;/code&gt; &lt;/p&gt;
&lt;h1 id="itertools"&gt;itertools&lt;/h1&gt;
&lt;p&gt;主要是用来穷举的时候它里面一些函数很好用... &lt;/p&gt;
&lt;p&gt;&lt;a href="https://docs.python.org/2/library/itertools.html"&gt;https://docs.python.org/2/library/itertools.html&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;itertools&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;product&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;combinations&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'ABCD'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'EFG'&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;product&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;    &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nb"&gt;print&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;...&lt;/span&gt;        &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;combinations&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt; &lt;span class="nb"&gt;print&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;    &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;...&lt;/span&gt;        &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;permutations&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt; &lt;span class="nb"&gt;print&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;...&lt;/span&gt;    &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'E'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'G'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'F'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="bitmap"&gt;bitmap&lt;/h1&gt;
&lt;p&gt;聪明一点的穷举需要用bitmap... 实测可以加速十倍...&lt;/p&gt;
&lt;h3 id="use-bitmap-for-combinations-2n-possibilities"&gt;use bitmap for combinations (2^N possibilities)&lt;/h3&gt;
&lt;p&gt;(N elements, each element 2 choices) &lt;br/&gt;
&lt;code&gt;for mask in xrange(1&amp;lt;&amp;lt;N): ...&lt;/code&gt; &lt;/p&gt;
&lt;h3 id="setclean-kth-bit"&gt;set/clean Kth bit&lt;/h3&gt;
&lt;p&gt;set: &lt;code&gt;bm |= 1&amp;lt;&amp;lt;k&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;clean: &lt;code&gt;bm &amp;amp;= ~(1&amp;lt;&amp;lt;k)&lt;/code&gt; &lt;/p&gt;
&lt;h3 id="count-nb-of-1s-in-a-bitmap"&gt;count nb of 1s in a bitmap&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;bin(bm).count('1')&lt;/code&gt; &lt;/p&gt;
&lt;h1 id="networkx_1"&gt;networkx&lt;/h1&gt;
&lt;p&gt;常用的图论算法都在里面了. nx最棒的是&lt;strong&gt;任何hashable的object都可以用来作为节点的index&lt;/strong&gt;, 再想想用C++的bgl, 简直蛋疼...
&lt;a href="https://networkx.readthedocs.io/en/stable/"&gt;https://networkx.readthedocs.io/en/stable/&lt;/a&gt; &lt;/p&gt;
&lt;h3 id="constructing-graph"&gt;constructing graph&lt;/h3&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;networkx&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;nx&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DiGraph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c1"&gt;# use `Graph` for undired graph, `MultiGraph` for dup-edges   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# any hashable obj can be used as node index   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# missing nodes will be automatically added   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# if G is undired(`Graph`), 1--&amp;gt;3 and 3--&amp;gt;1 will be added   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;nodes&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# nx ignores duplicate adding edges/nodes    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;nodes&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="c1"&gt;# outgoing edges from a node   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{}}&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;][&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;][&lt;/span&gt;&lt;span class="s1"&gt;'color'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'blue'&lt;/span&gt; &lt;span class="c1"&gt;# easily add edge properties    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s1"&gt;'color'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'blue'&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{}}&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# this is another way to add property   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edge&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s1"&gt;'color'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'blue'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'capacity'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{}},&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{}}&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;][&lt;/span&gt;&lt;span class="s1"&gt;'cat'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s1"&gt;'string node'&lt;/span&gt; &lt;span class="c1"&gt;# can also be: G.add_node('a', cat='string node')   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="s1"&gt;'cat'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s1"&gt;'string node'&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{}}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="digraph-topo-sort-cycle-detection-strongly-connected-component"&gt;DiGraph: topo-sort, cycle-detection, strongly connected component&lt;/h3&gt;
&lt;p&gt;&lt;a href="http://networkx.readthedocs.io/en/stable/reference/algorithms.shortest_paths.html"&gt;http://networkx.readthedocs.io/en/stable/reference/algorithms.shortest_paths.html&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;networkx&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;nx&lt;/span&gt;    &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DiGraph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;list&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;strongly_connected_components&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;]),&lt;/span&gt; &lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;]),&lt;/span&gt; &lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;]),&lt;/span&gt; &lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;]),&lt;/span&gt; &lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;])]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;topological_sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;list&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;simple_cycles&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;]]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;list&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;strongly_connected_components&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;]),&lt;/span&gt; &lt;span class="nb"&gt;set&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;])]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;shortest_path&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;shortest_path&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;shortest_path_length&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mi"&gt;3&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;shortest_path_length&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'weight'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# set attribut edge 'weight' as weight, (if not present, weight=1 )   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="undirected-graph-connected-component-mst"&gt;Undirected Graph: connected component, MST&lt;/h3&gt;
&lt;p&gt;&lt;a href="http://networkx.readthedocs.io/en/networkx-1.11/reference/generated/networkx.algorithms.mst.minimum_spanning_tree.html#networkx.algorithms.mst.minimum_spanning_tree"&gt;http://networkx.readthedocs.io/en/networkx-1.11/reference/generated/networkx.algorithms.mst.minimum_spanning_tree.html#networkx.algorithms.mst.minimum_spanning_tree&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&amp;gt;&amp;gt;&amp;gt; G = nx.Graph()   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; G.add_edge(1,2); G.add_edge(1,3); G.add_edge('a','b')   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; list( nx.connected_components(G) )   &lt;/span&gt;
&lt;span class="code-line"&gt;[set(['a', 'b']), set([1, 2, 3])]   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; G.add_edge(2,3)   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; mst =  nx.minimum_spanning_tree(G) # returns a new graph   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; mst.edges()   &lt;/span&gt;
&lt;span class="code-line"&gt;[('a', 'b'), (1, 2), (1, 3)]   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; G.add_edge(1,3,weight=2) # mst takes attribut 'weight', if no present, weight=1   &lt;/span&gt;
&lt;span class="code-line"&gt;&amp;gt;&amp;gt;&amp;gt; nx.minimum_spanning_tree(G).edges()   &lt;/span&gt;
&lt;span class="code-line"&gt;[('a', 'b'), (1, 2), (2, 3)]&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="maxflow"&gt;maxflow&lt;/h3&gt;
&lt;p&gt;&lt;a href="http://networkx.readthedocs.io/en/networkx-1.11/reference/algorithms.flow.html"&gt;http://networkx.readthedocs.io/en/networkx-1.11/reference/algorithms.flow.html&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;networkx&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;nx&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DiGraph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'x'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;3.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'x'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;1.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'a'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'c'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;3.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'c'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;5.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'d'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;4.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'d'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'e'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;2.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'c'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'y'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;2.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'e'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'y'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;3.0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;flow_value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;flow_dict&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;maximum_flow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'x'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'y'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;flow_value&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mf"&gt;3.0&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;flow_dict&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s1"&gt;'x'&lt;/span&gt;&lt;span class="p"&gt;][&lt;/span&gt;&lt;span class="s1"&gt;'b'&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mf"&gt;1.0&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="maximum-matching"&gt;maximum matching&lt;/h3&gt;
&lt;p&gt;NB: maxi&lt;strong&gt;mum&lt;/strong&gt; matching != maxim&lt;strong&gt;al&lt;/strong&gt; matching... &lt;br/&gt;
there are maximum-matching functions for general undir graph (&lt;code&gt;max_weight_matching&lt;/code&gt;) and for bipartitie graph (&lt;code&gt;maximum_matching&lt;/code&gt;), the one for bipartite graph is faster, the general one takes O(V**3).   &lt;/p&gt;
&lt;p&gt;&lt;a href="http://networkx.readthedocs.io/en/stable/reference/generated/networkx.algorithms.matching.max_weight_matching.html?highlight=maximum_matching"&gt;http://networkx.readthedocs.io/en/stable/reference/generated/networkx.algorithms.matching.max_weight_matching.html?highlight=maximum_matching&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Graph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edges_from&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;(1,2),(2,3),(3,4),(4,5)&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mate&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;max_weight_matching&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;maxcardinality&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="k"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="n"&gt;#mate&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;matched&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mate&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;is_bipartite&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;True&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mate&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;bipartite&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;maximum_matching&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mate&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;and there are vertex cover algorithms as well......     &lt;/p&gt;
&lt;h1 id="pulp_1"&gt;pulp&lt;/h1&gt;
&lt;p&gt;线性规划的库, 供了非常好用的接口来构造LP问题, 增加约束或者定义objective只要用&lt;code&gt;prob+=[expression]&lt;/code&gt;就好了, 基本上看看例子就能上手. 
面对选择问题的时候线性规划是不错的方法 -- 如果计算速度可以足够快的话... &lt;/p&gt;
&lt;p&gt;&lt;a href="https://pythonhosted.org/PuLP/pulp.html"&gt;https://pythonhosted.org/PuLP/pulp.html&lt;/a&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;pulp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpVariable&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"x"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpVariable&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'Integer'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# var category can be integer   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpProblem&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"myProblem"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;LpMinimize&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# add constraint   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="c1"&gt;# add objective   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c1"&gt;# solve using default solver   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;GLPK&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="c1"&gt;# or use glpk solver   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;LpStatus&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="s1"&gt;'Optimal'&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;objective&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# see objective value   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mf"&gt;8.0&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# see variable value    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mf"&gt;2.0&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;关于nx和pulp的应用可以参考&lt;a href="http://x-wei.github.com/codejam-2015-r2pbC.html"&gt;上篇文章&lt;/a&gt;.&lt;/p&gt;</content><category term="tech"/><category term="algorithm"/><category term="codejam"/><category term="python"/></entry><entry><title>codejam2015-round2-pbC 的三种解法</title><link href="https://x-wei.github.io/tech/codejam-2015-r2pbC.html" rel="alternate"/><published>2016-05-27T00:00:00+02:00</published><updated>2016-05-27T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-05-27:/tech/codejam-2015-r2pbC.html</id><summary type="html">&lt;p&gt;昨天做的一道codejam题目, 这个题目的三种解法都非常有代表性, 特此一记.    &lt;/p&gt;
&lt;p&gt;题目链接在这里:  &lt;br/&gt;
&lt;a href="https://code.google.com/codejam/contest/8234486/dashboard#s=p2"&gt;https://code.google.com/codejam/contest/8234486/dashboard#s=p2&lt;/a&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Elliot's parents speak French and English …&lt;/p&gt;&lt;/blockquote&gt;</summary><content type="html">&lt;p&gt;昨天做的一道codejam题目, 这个题目的三种解法都非常有代表性, 特此一记.    &lt;/p&gt;
&lt;p&gt;题目链接在这里:  &lt;br/&gt;
&lt;a href="https://code.google.com/codejam/contest/8234486/dashboard#s=p2"&gt;https://code.google.com/codejam/contest/8234486/dashboard#s=p2&lt;/a&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Elliot's parents speak French and English to him at home. He has heard a lot of words, but it isn't always clear to him which word comes from which language! Elliot knows one sentence that he's sure is English and one sentence that he's sure is French, and some other sentences that could be either English or French. If a word appears in an English sentence, it must be a word in English. If a word appears in a French sentence, it must be a word in French.    &lt;br/&gt;
Considering all the sentences that Elliot has heard, what is the minimum possible number of words that he's heard that must be words in both English and French?        &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Input     &lt;br/&gt;
The first line of the input gives the number of test cases, T. T test cases follow. Each starts with a single line containing an integer N. N lines follow, each of which contains a series of space-separated "words". Each "word" is made up only of lowercase characters a-z. The first of those N lines is a "sentence" in English, and the second is a "sentence" in French. The rest could be "sentences" in either English or French. (Note that the "words" and "sentences" are not guaranteed to be valid in any real language.)   &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Output     &lt;br/&gt;
For each test case, output one line containing "Case #x: y", where x is the test case number (starting from 1) and y is the minimum number of words that Elliot has heard that must be words in both English and French.   &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Limits   &lt;br/&gt;
1 ≤ T ≤ 25. &lt;br/&gt;
Each word will contain no more than 10 characters. &lt;br/&gt;
The two "known" sentences will contain no more than 1000 words each. &lt;br/&gt;
The "unknown" sentences will contain no more than 10 words each. &lt;br/&gt;
Small dataset &lt;br/&gt;
2 ≤ N ≤ 20. &lt;br/&gt;
Large dataset &lt;br/&gt;
2 ≤ N ≤ 200.   &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;我的codejam程序模板长这样:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;def readval(typ=int):   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    return typ( raw_input() )&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;def readvals(typ=int):   &lt;/span&gt;
&lt;span class="code-line"&gt;    return map( typ, raw_input().split() )&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;def testcase(cas):   &lt;/span&gt;
&lt;span class="code-line"&gt;    print 'Case #%d: %d' % ( cas, res )&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;if __name__=='__main__':   &lt;/span&gt;
&lt;span class="code-line"&gt;    T = int(raw_input())   &lt;/span&gt;
&lt;span class="code-line"&gt;    for i in xrange(T):   &lt;/span&gt;
&lt;span class="code-line"&gt;        testcase(i+1)&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="1-bruteforce-for-small-testcase"&gt;法1: 穷举 bruteforce (for small testcase)&lt;/h1&gt;
&lt;p&gt;在small set(N=20) 中, 对于那18个未知语言的句子, 每句可能是英语或法语. 那么穷举所有可能性, 然后选择双语单词最少的即可. 2^18约等于几十万 , 按说python还是可以handle的 (2^10=1k, 2^ 20=1M, python每秒大约能循环几百万次).    &lt;/p&gt;
&lt;h2 id="naive-bruteforce"&gt;naive bruteforce&lt;/h2&gt;
&lt;p&gt;生成所有的可能性组合, python的&lt;code&gt;itertools&lt;/code&gt;包里提供了&lt;a href="https://docs.python.org/2/library/itertools.html#itertools.combinations"&gt;combinations&lt;/a&gt;函数, &lt;code&gt;combinations(iterable, r)&lt;/code&gt;返回所有在iterable中大小为r的子集(的迭代器):    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;itertools&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;combinations&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;combinations&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'ABCD'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt; &lt;span class="nb"&gt;print&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'A'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'B'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'C'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'D'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;用&lt;code&gt;combination&lt;/code&gt;函数即可实现枚举每句话是英语还是法语的功能.    &lt;/p&gt;
&lt;p&gt;当每句话是英语还是法语已经确定以后, 可以用集合取交集的方法(&lt;code&gt;set1.intersection(set2)&lt;/code&gt;)得到两种语言一共有多少个重复的单词. 程序长这样:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;testcase&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;cas&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fast&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;enough&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readval&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;En&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readvals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Fr&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readvals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s1"&gt;'Case #%d: %d'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cas&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;En&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;intersection&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Fr&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;readvals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;engsubset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;allEn&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allFr&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;En&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;copy&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Fr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;copy&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;engsubset&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allEn&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allFr&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allEn&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;intersection&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;allFr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;possibleres&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;engsubset&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;combinations&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;l&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;possibleres&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;engsubset&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;possibleres&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s1"&gt;'Case #%d: %d'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cas&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;然而, 下载了small testcase以后运行程序, 速度还是不够快, 大约要十分钟才有结果 — 而codejam的提交时间限制是4分钟啊... 程序每次检查2^18种可能性, 但是由于每次检查都要进行集合的union和intersection操作(这种操作的效率并不高, 甚至C++里也是一样), 这个操作太耗费时间了所以不行...    &lt;/p&gt;
&lt;h2 id="bruteforce-using-bitmap"&gt;bruteforce using bitmap&lt;/h2&gt;
&lt;p&gt;需要更加聪明的穷举方法, 自然的想法就是用bitmap(或者叫bitvector?). 之前的两个基本操作都可以用bitmap完成:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;枚举各个句子的语言种类: 如果每个句子用一位来表示的话(1代表英语, 0代表法语), 那么用N位的bitmap即可表示一种情形. 这个bitmap只需从0增加到2^N-1, 就把2^N个可能性都遍历了. (实际上是2^N-2个可能性, 因为前两个句子已经确定语言了).    &lt;/li&gt;
&lt;li&gt;两种语言的词汇表进行union/intersection: 假设共有K个不同的单词, 那么用一个K位的bitmap即可表示一种语言包含了哪些单词. 然后集合的union和intersection即可表示为OR和AND的逻辑运算.    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;bit manipulation蛮subtle的, 不过习惯了就好... 另外python的integer可以任意长度, 不用像C/java那样考虑bitmap位数大于64的情况, 还是非常方便的. 代码如下:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;testcase&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;cas&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmap&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;instead&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;speedup&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;small&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!!&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readval&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readval&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;split&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sorted&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;K&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;distinct&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sentence&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;can&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;be&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reprensented&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;K&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nc"&gt;bit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmap&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;#construct&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;bm&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;scent&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;split&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;bm&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;|=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;bm&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;1e10&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;look&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;combinations&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;en&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;0&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;en&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;|=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k+2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;|=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bitmaps&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k+2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bin&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;en&lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'1'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s1"&gt;'Case #%d: %d'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cas&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;以上代码在我电脑上执行small的时候大约花费1分钟, 比最开始用set的速度提高了十倍. 当然, 对于large的case这种解法肯定就超时了...    &lt;/p&gt;
&lt;h1 id="2-maxflow_1"&gt;法2: 最大流 maxflow&lt;/h1&gt;
&lt;p&gt;这个方法也是官方&lt;a href="https://code.google.com/codejam/contest/8234486/dashboard#s=a&amp;amp;a=2"&gt;analysis&lt;/a&gt;里提供的答案. 如果将所有句子&lt;code&gt;S&lt;/code&gt;以及所有单词&lt;code&gt;w&lt;/code&gt;看作节点, 每个句子的节点&lt;code&gt;S&lt;/code&gt;于它包含的单词的节点&lt;code&gt;w&lt;/code&gt;相连, 问题转化成了从节点&lt;code&gt;S1&lt;/code&gt;到节点&lt;code&gt;S2&lt;/code&gt;的vertex cut问题 (选取最小的节点集合, 将该集合的节点去掉以后S1和S2不再联通).    &lt;/p&gt;
&lt;p&gt;然后这个问题又可以转为边的min cut问题: 只需要把每个单词节点w分成左右两个节点&lt;code&gt;w1&lt;/code&gt;和&lt;code&gt;w2&lt;/code&gt;, 并且这样添加边(假设w在句子S中):    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;w1--&amp;gt;w2&lt;/code&gt;, capacity=1   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;S--&amp;gt;w1&lt;/code&gt;, capacity=INF   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;w2--&amp;gt;S&lt;/code&gt;, capacity=INF   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;在这样构造的图里计算maxflow即可得到mincut, 也就是题目的答案...    &lt;/p&gt;
&lt;p&gt;在实现这个解法的时候用到了networkx这个包, 它提供了比bgl好用100倍的接口(虽然也比bgl慢差不多100倍 ==...). &lt;em&gt;任何hashable的object都可以用来作为节点的index&lt;/em&gt;, 所以写起来非常舒服, 15行搞定:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;testcase_maxflow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ind&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt; &lt;span class="c1"&gt;# using maxflow !   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;INF&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mf"&gt;1e10&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;networkx&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;nx&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;G&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DiGraph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;N&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;readval&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;        &lt;span class="n"&gt;words&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;readvals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;        &lt;span class="n"&gt;si&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'sent-&lt;/span&gt;&lt;span class="si"&gt;%d&lt;/span&gt;&lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;        &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;si&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;        &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;wd&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;    &lt;/span&gt;
&lt;span class="code-line"&gt;            &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="s1"&gt;'_l'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="s1"&gt;'_r'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;            &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;si&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="s1"&gt;'_l'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;INF&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;            &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add_edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="s1"&gt;'_r'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;si&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;INF&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;flow_value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;flow_dict&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;nx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;maximum_flow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'sent-0'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'sent-1'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="nb"&gt;print&lt;/span&gt; &lt;span class="s1"&gt;'Case #&lt;/span&gt;&lt;span class="si"&gt;%d&lt;/span&gt;&lt;span class="s1"&gt;: &lt;/span&gt;&lt;span class="si"&gt;%d&lt;/span&gt;&lt;span class="s1"&gt;'&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;ind&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nb"&gt;int&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;flow_value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;用这个代码即可轻松通过large case... maxflow的建模还真是艺术...orz   &lt;/p&gt;
&lt;h1 id="3-integer-linear-programming"&gt;法3: 线性规划 (integer) linear programming&lt;/h1&gt;
&lt;p&gt;写完上面那个解法以后, 我又看了看&lt;a href="https://www.go-hero.net/jam/15/name/linguo"&gt;大神&lt;/a&gt;的解法, 发现他居然用的是&lt;a href="https://pythonhosted.org/PuLP/pulp.html"&gt;pulp&lt;/a&gt;(python线性规划的包), 于是自己想了一下, 这个问题确实可以用线性规划来建模 !    &lt;/p&gt;
&lt;p&gt;首先说一句pulp这个包, 它提供了非常好用的接口来构造LP问题, 增加约束或者定义objective只要用&lt;code&gt;prob+=[expression]&lt;/code&gt;就好了, 可以说比AMPL好用不少... 下面是一个简单的例子:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="kn"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nn"&gt;pulp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpVariable&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"x"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpVariable&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'Integer'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# var category can be integer   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;LpProblem&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"myProblem"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;LpMinimize&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# add constraint   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="c1"&gt;# add objective   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c1"&gt;# solve using default solver   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;GLPK&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="c1"&gt;# or use glpk solver   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;LpStatus&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="s1"&gt;'Optimal'&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;prob&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;objective&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# see objective value   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mf"&gt;8.0&lt;/span&gt;   &lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# see variable value    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="mf"&gt;2.0&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;OK, 本题的建模过程如下:  &lt;br/&gt;
对于每一个句子&lt;code&gt;S&lt;/code&gt;, 定义binary的LP变量&lt;code&gt;Se&lt;/code&gt;, Se=1表示句子S为英语, =0表示为法语.  &lt;br/&gt;
对于每个单词&lt;code&gt;w&lt;/code&gt;, 定义两个binary变量&lt;code&gt;we&lt;/code&gt;, &lt;code&gt;wf&lt;/code&gt;, 表示单词w是英(法)语单词.  &lt;br/&gt;
然后, 再定义变量&lt;code&gt;wef&lt;/code&gt;, 它表示单词&lt;code&gt;w&lt;/code&gt;既是英语单词又是法语单词. 所以有这个逻辑关系: &lt;code&gt;wef = we AND wf&lt;/code&gt; 那么这种逻辑关系如何用线性约束描述呢? 可以这样: &lt;code&gt;wef &amp;gt;= we+wf-1&lt;/code&gt; 非常巧妙吧... &lt;br/&gt;
(&lt;a href="http://cs.stackexchange.com/questions/12102/express-boolean-logic-operations-in-zero-one-integer-linear-programming-ilp"&gt;这篇文章&lt;/a&gt;总结了各种逻辑关系用线性规划的描述方式, 写的得非常详细. )   &lt;/p&gt;
&lt;p&gt;要最小化的目标函数就是 &lt;code&gt;sum(wef)&lt;/code&gt; 了, 约束除了刚才那个&lt;code&gt;wef &amp;gt;= we+wf-1&lt;/code&gt;以外, 还要表达单词和句子之间的关系: 如果一个句子为英(法)语, 那么句子里的每一个单词都为英(法)语. 这是一个&lt;code&gt;se==&amp;gt;we&lt;/code&gt;的逻辑关系, 用线性约束表达为: &lt;code&gt;we&amp;gt;=se&lt;/code&gt;.    &lt;/p&gt;
&lt;p&gt;所以整个模型是:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;Minimize sum(wef)   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;st:   &lt;/span&gt;
&lt;span class="code-line"&gt;we &amp;gt;= se   &lt;/span&gt;
&lt;span class="code-line"&gt;wf &amp;gt;= (1-se)   &lt;/span&gt;
&lt;span class="code-line"&gt;wef &amp;gt;= we+wf-1   &lt;/span&gt;
&lt;span class="code-line"&gt;Se[0]==1, Se[1]==0&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;用pulp编写的代码如下:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;def&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;testcase&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ind&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;formulate&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;it&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;linear&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;programming&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;readval&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sentc&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;sentc&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;readvals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sentc&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;-1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sorted&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;allwords&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;wordsindex&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="n"&gt;words&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mapping&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;its&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LpProblem&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'Bilingual'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LpMinimize&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LP&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;variables&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('Se_'+str(i), cat='Binary') for i in xrange(N) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;scentence&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;english&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('we_'+str(j), cat='Binary') for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;english&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('wf_'+str(j), cat='Binary') for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;french&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('wef_'+str(j), cat='Binary') for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;BOTH&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;en&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;sum&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;0&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;si&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sentc&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;si&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wordsindex&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;wd&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;xrange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="o"&gt;~&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;GLPK&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;msg&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;solve&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pb&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;objective&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s1"&gt;'Case #%d: %d'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ind&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;res&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;以上代码在small上运行约1分钟, large约3分钟.    &lt;/p&gt;
&lt;p&gt;另外我发现&lt;a href="https://www.go-hero.net/jam/15/name/liutianren"&gt;另一个大神&lt;/a&gt;代码里没有用Binary/Integer的lp变量, 也就是说他用的是连续的线性规划! 当我把变量的定义改成:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('Se_'+str(i), 0, 1) for i in xrange(N) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Se&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;scentence&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;english&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('we_'+str(j), 0) for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;english&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('wf_'+str(j), 0) for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wf&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;french&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; LpVariable('wef_'+str(j), 0) for j in xrange(M) &lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;wef&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;indicator&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;BOTH&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;en&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这样以后, 得到的结果还是正确的!! (不过代码运行时间没有显著的提高).    &lt;/p&gt;
&lt;p&gt;所以是这个模型中的矩阵满足&lt;a href="https://en.wikipedia.org/wiki/Unimodular_matrix#Total_unimodularity"&gt;totally unimodular&lt;/a&gt;性质?  &lt;br/&gt;
不过这个模型似乎并不满足wikipedia里写的那个充分条件?...@@  &lt;br/&gt;
&lt;a href="https://kunigami.wordpress.com/2013/08/12/tu-matrix-recognition/"&gt;这里&lt;/a&gt;有一篇真•大神的文章是讲如何识别TU矩阵的 (tl;dr......), 那么是不是各种solver内部已经有了自动判断TU的代码, 所以这两种程序的运行时间差不多?...    &lt;/p&gt;
&lt;p&gt;总而言之这道题目还是非常有意思的, 三种解法都很有代表性, 这里的技巧估计在codejam里会经常用到...    &lt;/p&gt;</content><category term="tech"/><category term="algorithm"/><category term="codejam"/></entry><entry><title>[Algorithms II] Week 6-3 Intractability</title><link href="https://x-wei.github.io/notes/algoII_week6_3_intractability.html" rel="alternate"/><published>2016-02-23T00:00:00+01:00</published><updated>2016-02-23T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-02-23:/notes/algoII_week6_3_intractability.html</id><summary type="html">&lt;h1 id="1-introduction-to-intractability"&gt;1. Introduction to Intractability&lt;/h1&gt;
&lt;p&gt;recall model of computation: DFA &lt;br/&gt;
a &lt;em&gt;univeral&lt;/em&gt; model of computation: turing machine  &lt;br/&gt;
→ no more powerful model of computation.  &lt;br/&gt;
Turing machine can compute any function that can be computed by a physically harnessable process of the natural world.    &lt;/p&gt;
&lt;p&gt;bottom line: turing machine is a simple and universal …&lt;/p&gt;</summary><content type="html">&lt;h1 id="1-introduction-to-intractability"&gt;1. Introduction to Intractability&lt;/h1&gt;
&lt;p&gt;recall model of computation: DFA &lt;br/&gt;
a &lt;em&gt;univeral&lt;/em&gt; model of computation: turing machine  &lt;br/&gt;
→ no more powerful model of computation.  &lt;br/&gt;
Turing machine can compute any function that can be computed by a physically harnessable process of the natural world.    &lt;/p&gt;
&lt;p&gt;bottom line: turing machine is a simple and universal model of computation.    &lt;/p&gt;
&lt;p&gt;Q. which algos are &lt;em&gt;useful in practice&lt;/em&gt;?   &lt;/p&gt;
&lt;p&gt;useful in practice = polynomial time for all inputs   &lt;/p&gt;
&lt;p&gt;def. a pb is &lt;strong&gt;intractable&lt;/strong&gt; if it cannot be solved in polynomial time.    &lt;/p&gt;
&lt;p&gt;2 pbs that &lt;em&gt;can be proved&lt;/em&gt; to require exp time:    &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Given a constant-size programme, does it halt in &amp;lt;=K steps ?   &lt;/li&gt;
&lt;li&gt;Given a N*N chess board position, can the first player force a win ?   &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Bad news: very few pbs can be proved to require exp time...   &lt;/p&gt;
&lt;h1 id="2-search-problems"&gt;2. Search Problems&lt;/h1&gt;
&lt;p&gt;**Four fundamental problems: **   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;LSLOVE&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Given a system of linear equations, find a solution &lt;br/&gt;
var: real numbers &lt;br/&gt;
→ guassian elimination   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;LP&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Given a system of linear inequaties, find a solution. (not necessarily find the opt) &lt;br/&gt;
var: real numbers   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;ILP&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Given a system of linear inequaties, find a &lt;strong&gt;0-1&lt;/strong&gt; solution.  &lt;br/&gt;
var: 0 or 1   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;SAT&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Given a system of &lt;em&gt;boolean equations&lt;/em&gt;, find a binary solution.    &lt;/p&gt;
&lt;p&gt;Which ones of the 4 foundamental pbs have poly-time solutions?   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;LSLOVE: Gaussian elimination works in O(n3)   &lt;/li&gt;
&lt;li&gt;LP: Ellipsoid works in poly-time (simplex also poly-time &lt;em&gt;in practice&lt;/em&gt;..)   &lt;/li&gt;
&lt;li&gt;ILP, SAT: No poly-time algorithm known (or believed to exist) !   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;All 4 pbs are examples of search problems.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Search pb&lt;/strong&gt;: given an instance &lt;code&gt;I&lt;/code&gt;, find a solution &lt;code&gt;S&lt;/code&gt; / report there's no solution.  &lt;br/&gt;
&lt;em&gt;requirement&lt;/em&gt;: able to efficiently (poly-time) &lt;em&gt;check&lt;/em&gt; that &lt;code&gt;S&lt;/code&gt; is a solution. (that's the case for the above 4 fundamental pbs)   &lt;/p&gt;
&lt;p&gt;another example:  &lt;br/&gt;
&lt;strong&gt;FACTOR&lt;/strong&gt;: given a n-bit integer, find a nontrival factor.  &lt;br/&gt;
(given a solution, simply need to long-divide to check...)   &lt;/p&gt;
&lt;h1 id="3-p-vs-np"&gt;3. P vs. NP&lt;/h1&gt;
&lt;p&gt;def. &lt;strong&gt;NP&lt;/strong&gt; is the class of all search pbs. (ie. solution be checked efficiently)  &lt;br/&gt;
NB: classical definition limits to yes-no pbs... &lt;br/&gt;
Significance: NP pbs are what scientists and engineers &lt;em&gt;aspire to compute feasibly&lt;/em&gt;. &lt;br/&gt;
examples:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;P&lt;/strong&gt; is the class of search pbs that &lt;em&gt;are solvable&lt;/em&gt; in poly-time.    &lt;/p&gt;
&lt;p&gt;(What scientists and engineers &lt;em&gt;do compute feasibly&lt;/em&gt;.)   &lt;/p&gt;
&lt;p&gt;examples: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Nondeterminism&lt;/strong&gt; &lt;br/&gt;
Nondeterminism machine can &lt;em&gt;guess&lt;/em&gt; the solution (donot exist in natural world..). → NFA tries to simulate such a machine... &lt;br/&gt;
Ex. &lt;code&gt;int[] a = new int[N];&lt;/code&gt; &lt;br/&gt;
・ Java: initializes entries to 0 . &lt;br/&gt;
・ Nondeterministic machine: &lt;em&gt;initializes entries to the solution!&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;NP: &lt;em&gt;Search problems solvable in poly time on a nondeterministic Turing machine&lt;/em&gt;.    &lt;/p&gt;
&lt;p&gt;Extended Church-Turing thesis: &lt;br/&gt;
P: Search pbs solvable in poly time &lt;em&gt;in natural world&lt;/em&gt;.    &lt;/p&gt;
&lt;p&gt;do we have non-determinism in natural world? ---&amp;gt; natural computers ?  &lt;br/&gt;
ex. STEINER tree: set of segments connecting given N points.  &lt;br/&gt;
use soap → doesn't really work... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;another example for P/NP: automating creativity &lt;br/&gt;
&lt;em&gt;being creative VS appreciating creativity&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;p&gt;The central question: does P=NP?  &lt;br/&gt;
(can you alway avoid brute-force searching and do better?) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image005.png"/&gt; &lt;br/&gt;
Millennium prize by Clay instute. &lt;br/&gt;
(among all ways of earning 1M dollars, this might be the most complicated way... @_@...)   &lt;/p&gt;
&lt;h1 id="4-classifying-problems"&gt;4. Classifying Problems&lt;/h1&gt;
&lt;p&gt;classify pbs like classifying elements into perodic table.    &lt;/p&gt;
&lt;p&gt;key pb: satisfiablity &lt;br/&gt;
SAT. given a sys of boolean eq, find a solution.    &lt;/p&gt;
&lt;p&gt;exhaustive search: try 2^n possible solutions.  &lt;br/&gt;
conjecture: no poly-time algo for SAT (ie. intractable)   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Assumption&lt;/strong&gt;: assume the intractability for SAT. &lt;br/&gt;
Tool: reduction &lt;br/&gt;
def. pb X reduces to pb Y: we can solve pb X with the algo for pb Y.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;if SAT poly-reduces to pb Y ⇒ pb Y in (probably) intractable.   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3 id="sat-poly-reduces-to-ilp"&gt;SAT poly-reduces to ILP&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image007.png"/&gt; &lt;br/&gt;
(all SAT pb can be reduced to 3SAT)   &lt;/p&gt;
&lt;p&gt;⇒ can be converted to an ILP pb:  &lt;br/&gt;
for each eq, introduce a var Ci: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h1 id="5-np-completeness_1"&gt;5. NP-Completeness&lt;/h1&gt;
&lt;blockquote&gt;
&lt;p&gt;def. an NP pb is &lt;strong&gt;NP-complete&lt;/strong&gt; if all pbs in NP poly-reduces to it.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;prop. &lt;em&gt;SAT id NP-complete.&lt;/em&gt; &lt;br/&gt;
any pb in NP poly-reduces to SAT (reverse direction as last lecture) &lt;br/&gt;
pf sketch: convert non-dertiministic turing machine notation to SAT notation...   &lt;/p&gt;
&lt;p&gt;cor. poly time algo for SAT iff P=NP...   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ there pbs are equivalent !    &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image014.png"/&gt; &lt;br/&gt;
summary:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image015.png"/&gt; &lt;/p&gt;
&lt;p&gt;==... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;h1 id="6-coping-with-intractability"&gt;6. Coping with Intractability&lt;/h1&gt;
&lt;h3 id="exploit-intractability"&gt;exploit intractability&lt;/h3&gt;
&lt;p&gt;cryptography ecopoits the hardness of FACTOR pb &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;p&gt;Can factor an n-bit integer in n 3 steps on a "&lt;em&gt;quantum computer&lt;/em&gt;.”   &lt;/p&gt;
&lt;h3 id="coping-with-intractability"&gt;Coping with intractability&lt;/h3&gt;
&lt;p&gt;relax one of desired features...   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;special cases   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Develop a heuristic, and hope it produces a good solution.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;no guarantee &lt;br/&gt;
ex. TSP   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Approximation algorithm. Find solution of provably good quality.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image019.png"/&gt; &lt;/p&gt;
&lt;h3 id="halmiton-path"&gt;Halmiton path&lt;/h3&gt;
&lt;p&gt;remark: Euler path (each edge once) easy, Halmiton path (each vertex once) NPC... &lt;br/&gt;
dfs solution for Halmiton path:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Halmiton&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nb&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Halmiton&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;paths&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Halmiton&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Graph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Graph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;depth&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;depth&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="k"&gt;false&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;depth&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;flase&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;backtrack&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_3_intractability/pasted_image020.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 6-2 Linear Programming</title><link href="https://x-wei.github.io/notes/algoII_week6_2_LP.html" rel="alternate"/><published>2016-02-21T17:00:00+01:00</published><updated>2016-02-21T17:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-02-21:/notes/algoII_week6_2_LP.html</id><summary type="html">&lt;p&gt;simplex algo: top 10 algo of the 20th century (ever?).   &lt;/p&gt;
&lt;p&gt;what is linear programming:  &lt;br/&gt;
&lt;em&gt;a general problem-solving model&lt;/em&gt; that works for:  &lt;br/&gt;
shortest-path, maxflow, MST, matching, assignment, ...   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h1 id="1-brewer-s-problem"&gt;1. Brewer-'s Problem&lt;/h1&gt;
&lt;p&gt;toy example: choose products to maximize profit.  &lt;br/&gt;
... &lt;br/&gt;
&lt;em&gt;feasible region&lt;/em&gt;: a convex polygon.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ optimum solution appears at an extreme point.    &lt;/p&gt;
&lt;p&gt;standard form …&lt;/p&gt;</summary><content type="html">&lt;p&gt;simplex algo: top 10 algo of the 20th century (ever?).   &lt;/p&gt;
&lt;p&gt;what is linear programming:  &lt;br/&gt;
&lt;em&gt;a general problem-solving model&lt;/em&gt; that works for:  &lt;br/&gt;
shortest-path, maxflow, MST, matching, assignment, ...   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h1 id="1-brewer-s-problem"&gt;1. Brewer-'s Problem&lt;/h1&gt;
&lt;p&gt;toy example: choose products to maximize profit.  &lt;br/&gt;
... &lt;br/&gt;
&lt;em&gt;feasible region&lt;/em&gt;: a convex polygon.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ optimum solution appears at an extreme point.    &lt;/p&gt;
&lt;p&gt;standard form of LP   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;n non-neg variables (j=1..n)   &lt;/li&gt;
&lt;li&gt;m linear euqations (i=1..m)   &lt;/li&gt;
&lt;li&gt;input: a_ij, c_j, b_i   &lt;/li&gt;
&lt;li&gt;output: x_j   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image003.png"/&gt; &lt;br/&gt;
to convert &lt;em&gt;inequality&lt;/em&gt; to &lt;em&gt;equality (as in the standard form above)&lt;/em&gt;: add slack var!  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;def. convex set &lt;br/&gt;
for any a and b in set ⇒ 1/2(a+b) is also in set.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;extreme point:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;def. &lt;strong&gt;extreme point&lt;/strong&gt; &lt;br/&gt;
is a point in set that cannot be written as 1/2(a+b) with a b distinct.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;extreme point property:  &lt;br/&gt;
if there exists an potimal solution, then there exists one that is an extreme point.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;nb of extreme point is finite   &lt;/li&gt;
&lt;li&gt;but this nb can be exponential   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;greedy property:  &lt;br/&gt;
&lt;em&gt;extreme point is optimal iff no better adj extreme points.&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-simplex-algorithm"&gt;2. Simplex Algorithm&lt;/h1&gt;
&lt;p&gt;algo. simplex   &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;start at some point   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;pivot&lt;/strong&gt; from one extreme point to an adj one (never decrease the obj fcn)   &lt;/li&gt;
&lt;li&gt;repeat until optimal   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;We're using the "basis" and "pivoting" to solve LP. &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;def. &lt;strong&gt;basis&lt;/strong&gt; (基变量) is a subset (size=m) of the n variables.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;vars in basis are always non-zero...   &lt;/p&gt;
&lt;p&gt;basic feasible solution:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;set n-m non-basis vars to 0   &lt;/li&gt;
&lt;li&gt;solve for remaining m vars (with m constraints)   &lt;/li&gt;
&lt;li&gt;if unique and feasible (matrix invertable)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;algo:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;initial basic-feasible-solution: start slack vars as basis.    &lt;/li&gt;
&lt;li&gt;choose a non-basic var as &lt;strong&gt;pivot&lt;/strong&gt;, add it into basis, take some basis var out   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex. pick B as pivot var using constraint 2 (2nd equation): &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;why picking var B? → its obj coeff is positive   &lt;/li&gt;
&lt;li&gt;why pivot on 2nd constraint (5A+15B+Sc=480)? →    &lt;ul&gt;
&lt;li&gt;RHS &amp;gt; 0 (preserves feasibility)   &lt;/li&gt;
&lt;li&gt;minimum ratio rule: min(480/15, 160/4, 1190/20)   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;stop when no obj-coeff is positive   &lt;/p&gt;
&lt;h1 id="3-simplex-implementations"&gt;3. Simplex Implementations&lt;/h1&gt;
&lt;p&gt;encode standard LP formulation into java 2d array:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Simplex&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="err"&gt;[][]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Simplex&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="err"&gt;[][]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;A&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;m+1&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;n+m+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;A&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j-n&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;n+m&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;simplex algo: just transform initial 2d array into final solution.    &lt;/p&gt;
&lt;h3 id="choosing-pivot-variable-find-entering-column"&gt;choosing pivot variable (find entering column)&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;Bland's rule.&lt;/strong&gt; find the first column whose obj-coeff is positive.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bland&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="choosing-pivot-constraint-find-entering-row"&gt;choosing pivot constraint (find entering row)&lt;/h3&gt;
&lt;p&gt;minimum ratio rule (if a tie, choose first row).    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;minRatioRule&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;continue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;==-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;m+n&lt;/span&gt;&lt;span class="o"&gt;]/&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;m+n&lt;/span&gt;&lt;span class="o"&gt;]/&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="do-the-pivot-column-q-row-p"&gt;do the pivot (column q, row p)&lt;/h3&gt;
&lt;p&gt;like Guassian elimination:    &lt;/p&gt;
&lt;p&gt;make var q disappear on each row (except for row p); &lt;br/&gt;
on row p: make var q's coeff become 1.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]*&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]/&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;/=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;so the simplex algo is:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;solve&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;true&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;bland&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="o"&gt;==-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="c1"&gt;; // optimal if -1   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;minRatioRule&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;&lt;span class="o"&gt;==-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="c1"&gt;; // unbounded if -1   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;pivot&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;,&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;final solution is just in the array: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;remarkable property&lt;/strong&gt; &lt;br/&gt;
&lt;em&gt;in typical applications&lt;/em&gt;, simplex terminates after at most 2(m+n) pivots. — whereas nb of extreme points is exp in n !! &lt;br/&gt;
ie. LINEAR time in practice!!   &lt;/p&gt;
&lt;p&gt;other pivot rules:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;h3 id="degeneracy"&gt;degeneracy&lt;/h3&gt;
&lt;p&gt;when choosing new basis, still stay in the same extreme point...  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image010.png"/&gt; &lt;br/&gt;
→ might cause cycling &lt;br/&gt;
→ bland's rule guarantees finite number of pivots   &lt;/p&gt;
&lt;p&gt;further improvement:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;Best practice. &lt;em&gt;Don't implement it yourself......&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image013.png"/&gt; &lt;br/&gt;
(AMPL是个好东西...)   &lt;/p&gt;
&lt;p&gt;算法的力量:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image015.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-linear-programming-reductions_1"&gt;4. Linear Programming Reductions&lt;/h1&gt;
&lt;h3 id="reduction-to-std-form-equalities"&gt;reduction to std form (equalities)&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;Minimization problem: max -1*obj   &lt;/li&gt;
&lt;li&gt;ineq constraints: add slack var   &lt;/li&gt;
&lt;li&gt;unbounded var X: replace with X=X0-X1, X0&amp;gt;=0, X1&amp;gt;=0   &lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="modeling-of-lp"&gt;modeling of LP&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;identify variables   &lt;/li&gt;
&lt;li&gt;define constraints   &lt;/li&gt;
&lt;li&gt;define objective fcn   &lt;/li&gt;
&lt;li&gt;convert to std form   &lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="maxflow-by-lp"&gt;maxflow by LP&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;variables: x_uv = flow on edge uv   &lt;/li&gt;
&lt;li&gt;constraints: capacity, flow conservation   &lt;/li&gt;
&lt;li&gt;obj: net flow to t   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;p&gt;can use LP to solve mincost maxflow easily...   &lt;/p&gt;
&lt;h3 id="max-cardinality-bipartite-matching-by-lp"&gt;max cardinality bipartite matching by LP&lt;/h3&gt;
&lt;p&gt;input: bipartite graph &lt;br/&gt;
goal: max cardinatlity matching (set of vertex-disjoint edges) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image017.png"/&gt; &lt;br/&gt;
can be reduced to maxflow (见algolab...)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;var: x_ij = indicator of person i assigned to job j (0&amp;lt;=x_ij&amp;lt;=1)   &lt;/li&gt;
&lt;li&gt;constraints: vertex-disjoint   &lt;/li&gt;
&lt;li&gt;obj: sum of all x_ij   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;p&gt;non-trival: cause this is an INTEGER LP...    &lt;/p&gt;
&lt;p&gt;Th (Von Neumann) (and Poincare?..)  &lt;br/&gt;
if all RHS=1 ⇒ &lt;em&gt;all extreme points of the polyhedron have integer coord&lt;/em&gt;.   &lt;/p&gt;
&lt;h3 id="and-many-others"&gt;and many others...&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_2_LP/pasted_image019.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;the profound question: Is there a universal problem-solving model ?&lt;/strong&gt; &lt;br/&gt;
→ P/NP...   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;"For the time being, the closest thing that we have to universal problem-solving model is LP "&lt;/strong&gt; &lt;/p&gt;
&lt;/blockquote&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 6-1 Reductions</title><link href="https://x-wei.github.io/notes/algoII_week6_1_reductions.html" rel="alternate"/><published>2016-02-19T09:00:00+01:00</published><updated>2016-02-19T09:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-02-19:/notes/algoII_week6_1_reductions.html</id><summary type="html">&lt;p&gt;Goal: classify problems according to computational requirements. &lt;br/&gt;
bad new: for huge number of pbs we don't know...  &lt;/p&gt;
&lt;h1 id="1-introduction-to-reductions"&gt;1. Introduction to Reductions&lt;/h1&gt;
&lt;p&gt;shifing gears:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;from individual problems to problem-solving models.   &lt;/li&gt;
&lt;li&gt;from linear/quard to polynomial/exponential pbs  &lt;/li&gt;
&lt;li&gt;from implementation details to conceptual framwork  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;suppose we could (not) solve pb X efficiently …&lt;/p&gt;</summary><content type="html">&lt;p&gt;Goal: classify problems according to computational requirements. &lt;br/&gt;
bad new: for huge number of pbs we don't know...  &lt;/p&gt;
&lt;h1 id="1-introduction-to-reductions"&gt;1. Introduction to Reductions&lt;/h1&gt;
&lt;p&gt;shifing gears:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;from individual problems to problem-solving models.   &lt;/li&gt;
&lt;li&gt;from linear/quard to polynomial/exponential pbs  &lt;/li&gt;
&lt;li&gt;from implementation details to conceptual framwork  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;suppose we could (not) solve pb X efficiently &lt;br/&gt;
⇒ what else pbs could (not) we solve efficiently ?  &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;def. reduction&lt;br/&gt;
Pb X &lt;strong&gt;reduces to&lt;/strong&gt; pb Y if you can use an algo that solves Y to solve X.   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image.png"/&gt;&lt;br/&gt;
for an instance of pb X → transform it into an instance of pb Y → translate the solution for Y to solution for X.&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;ex1. finding median can reduce to sorting... cost = NlogN+1&lt;br/&gt;
ex1. element distinctness can reduce to sorting... cost = NlogN + N  &lt;/p&gt;
&lt;h1 id="2-designing-algorithms"&gt;2. Designing Algorithms&lt;/h1&gt;
&lt;p&gt;algo design: by reduction to problems that we know how to solve (sorting/shortest path/flow/...)  &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h3 id="ex1-convex-hull-reduces-to-sorting"&gt;ex1. convex hull reduces to sorting&lt;/h3&gt;
&lt;p&gt;Gram scan algo... (discussed in algo-I course)&lt;br/&gt;
cost = NlogN + N&lt;br/&gt;
algo. Gram scan  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;pick a point with smallest y-coord  &lt;/li&gt;
&lt;li&gt;sort all points by polar angle wrt the picked point   &lt;/li&gt;
&lt;li&gt;consider points in this order, discard points that creates clockwise turn   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h3 id="ex2-undirected-shortest-path-nonneg-weights-reduces-to-directed-shortest-path"&gt;ex2. undirected shortest path (nonneg weights) reduces to directed shortest path&lt;/h3&gt;
&lt;p&gt;cost: ElogV + E&lt;br/&gt;
algo. replace each undir-edge by 2 dir-edge...  &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image004.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-establishing-lower-bounds_1"&gt;3. Establishing Lower Bounds&lt;/h1&gt;
&lt;p&gt;goal: prove that a pb requires (at least) a certain nb of steps.   &lt;/p&gt;
&lt;p&gt;ex. any compare-based sorting requires NlogN compares. log(N!) = NlogN  &lt;/p&gt;
&lt;p&gt;Bad news: very hard to estibalish lower bounds.&lt;br/&gt;
Good new: can spread the lower bound NlogN by reducing to sorting (if cost of reduction is small).   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;def. linear-time reduction&lt;br/&gt;
pb X linear-time reduces to pb Y if X can be solved with: &lt;br/&gt;
1. linear nb of op for reduction&lt;br/&gt;
2. constant nb of calles to Y  &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;ex. almost all reductions we've seen so far...   &lt;/p&gt;
&lt;h3 id="ex-proof-of-lower-bound-for-convex-hull"&gt;ex. proof of lower bound for convex hull&lt;/h3&gt;
&lt;p&gt;prop. sorting linear-time reduces to convex hull &lt;br/&gt;
(注意这次是反向的! )&lt;br/&gt;
pf. &lt;br/&gt;
for an instance of sorting: x1 ... xn&lt;br/&gt;
⇒ convert to convex hull instance: &lt;em&gt;(x1, x1^2), ... , (xn, xn^2)&lt;/em&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ implication: all (ccw-based) convex hull algo cannot be easier than NlgN ! (otherwise sorting would be easier..)   &lt;/p&gt;
&lt;p&gt;lesson: Establishing lower bounds through reduction is an important tool in guiding algorithm design efforts.&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-classifying-problems_1"&gt;4. Classifying Problems&lt;/h1&gt;
&lt;p&gt;prove that pb X and pb Y have the same complexity:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;show X linear-time reduces to Y  &lt;/li&gt;
&lt;li&gt;show Y linear-time reduces to X  &lt;/li&gt;
&lt;li&gt;conclude that X Y have the same complexity (even if we don't know what it is)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex. sorting and convex hull... &lt;br/&gt;
一个囧囧的脑洞: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h3 id="ex-integer-arithmetic-reductions-integer-multiplication"&gt;ex. integer arithmetic reductions: integer multiplication&lt;/h3&gt;
&lt;p&gt;integer multiplication: of two N-bit integers. &lt;br/&gt;
Its complexity (unknown) is denoted as M(N)&lt;br/&gt;
brute force: N^2 ops  → so M(N) = Omega(N2)&lt;br/&gt;
many other integer ops can reduce to integer multiplication: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image009.png"/&gt;&lt;br/&gt;
what is M(N)?&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h3 id="ex-linear-algebra-reductions-matrix-multiplication"&gt;ex. linear-algebra reductions: matrix multiplication&lt;/h3&gt;
&lt;p&gt;compute product of 2 N*N matrices. &lt;br/&gt;
Its complexity (unknown) is denoted as MM(N)&lt;br/&gt;
brute force: N^3&lt;br/&gt;
operations that can reduce to matrix-multiplication:&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image011.png"/&gt;&lt;br/&gt;
what is MM(N)?&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;h3 id="summary"&gt;summary&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week6_1_reductions/pasted_image013.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 5-2 Data Compression</title><link href="https://x-wei.github.io/notes/algoII_week5_2.html" rel="alternate"/><published>2016-01-04T00:00:00+01:00</published><updated>2016-01-04T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2016-01-04:/notes/algoII_week5_2.html</id><summary type="html">&lt;h1 id="1-introduction-to-data-compression"&gt;1. Introduction to Data Compression&lt;/h1&gt;
&lt;p&gt;pb: reduce the size of a file, to save space/time for storing/transmitting. &lt;br/&gt;
applications: generic file compression(gzip), multimedia (mp3), communication(skype).   &lt;/p&gt;
&lt;p&gt;From binary data &lt;code&gt;B&lt;/code&gt;, ⇒ generate a compressed representation &lt;code&gt;C(B)&lt;/code&gt;. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image.png"/&gt;&lt;br/&gt;
&lt;strong&gt;lossless compression&lt;/strong&gt;: get exactly &lt;code&gt;B&lt;/code&gt; from &lt;code&gt;C(B)&lt;/code&gt;&lt;br/&gt;
&lt;strong&gt;compression ratio&lt;/strong&gt;: &lt;code&gt;|C(B …&lt;/code&gt;&lt;/p&gt;</summary><content type="html">&lt;h1 id="1-introduction-to-data-compression"&gt;1. Introduction to Data Compression&lt;/h1&gt;
&lt;p&gt;pb: reduce the size of a file, to save space/time for storing/transmitting. &lt;br/&gt;
applications: generic file compression(gzip), multimedia (mp3), communication(skype).   &lt;/p&gt;
&lt;p&gt;From binary data &lt;code&gt;B&lt;/code&gt;, ⇒ generate a compressed representation &lt;code&gt;C(B)&lt;/code&gt;. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image.png"/&gt;&lt;br/&gt;
&lt;strong&gt;lossless compression&lt;/strong&gt;: get exactly &lt;code&gt;B&lt;/code&gt; from &lt;code&gt;C(B)&lt;/code&gt;&lt;br/&gt;
&lt;strong&gt;compression ratio&lt;/strong&gt;: &lt;code&gt;|C(B)|/|B|&lt;/code&gt;(||means number of &lt;em&gt;bits&lt;/em&gt;)  &lt;/p&gt;
&lt;h3 id="tools"&gt;Tools&lt;/h3&gt;
&lt;p&gt;extension to stdio libraries: read/write &lt;em&gt;bits&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readBoolean&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // read 1 bit and return as a boolean  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readChar&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // read 8 bits and return a char  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readChar&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // read r (&amp;lt;=8) bits and return a char  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;similar&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;method&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="nv"&gt;long&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="nv"&gt;double&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;isEmpty&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // is bitstream empty?  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;b&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // write 1 bit  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;c&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // write 8 bits  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;c&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // write r (least-significant) bits of c  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;similar&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;method&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="nv"&gt;long&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="nv"&gt;double&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // might add some byte alignment bits   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;usage example: store a date 12/31/1999&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;universal date compression?&lt;br/&gt;
&lt;strong&gt;prop&lt;/strong&gt;. NO algorithm can compress every bitstring.&lt;br/&gt;
pf. by contradiction: repeatedly compress the bitstring ⇒ bit length goes to 0.   &lt;/p&gt;
&lt;h1 id="2-run-length-coding_1"&gt;2. Run-Length Coding&lt;/h1&gt;
&lt;p&gt;one simple type of redundancy in bitstream: long runs of repeated bits. &lt;br/&gt;
⇒ use &lt;em&gt;4-bit counts&lt;/em&gt; to represent alternating 1s and 0s. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;question1: how many bits to represent counts ? ⇒ pick 8 bits (just tradeoff)  &lt;/li&gt;
&lt;li&gt;question2: what if run length is bigger than max length(2^8)? ⇒ just add length=0 of the alternating bit...   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;application: JPEG...   &lt;/p&gt;
&lt;p&gt;code:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;RunLength&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;R&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;256&lt;/span&gt;&lt;span class="c1"&gt;; // max run length  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;compress&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;oldbit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;false&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;isEmpty&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;readBoolean&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="nv"&gt;old&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;oldbit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;,&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;R&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;,&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;,&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;expand&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;false&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;isEmpty&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;readInt&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;lgR&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;i&amp;lt;l;i++)  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;bit&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="3-huffman-compression"&gt;3. Huffman Compression&lt;/h1&gt;
&lt;p&gt;classique...   &lt;/p&gt;
&lt;p&gt;idea: &lt;em&gt;variable length code&lt;/em&gt;. &lt;br/&gt;
ex. Morse code, more freq chars use less chars. &lt;br/&gt;
→ pb: ambiguity? one code is the prefix of another... &lt;br/&gt;
→ need to use &lt;em&gt;prefix-free code&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;⇒ use a trie to represent the prefix-free code, in bitstream, use a binary trie: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h3 id="huffman-trie-node"&gt;Huffman Trie Node&lt;/h3&gt;
&lt;p&gt;define trie nodes having frequences:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;ch&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;// only used for leaves, null for internal nodes  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;freq&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;left&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;right&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;// left--&amp;gt;0, right--&amp;gt;1  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;ch&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;freq&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;left&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;right&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="c1"&gt;//...}  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;isLeaf&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;left&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;right&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;compareTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;that&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;freq&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nx"&gt;that&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;freq&lt;/span&gt;&lt;span class="p"&gt;;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;expansion&lt;/strong&gt;&lt;br/&gt;
&lt;em&gt;in the bitstream, we first put the (serialized) trie in the head.&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;expand&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;getTrie&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; //   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;readInt&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // number of chars in string  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;; i&amp;lt;N; i++){  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;isLeaf&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;BinaryStdIn&lt;/span&gt;.&lt;span class="nv"&gt;readBoolean&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;ch&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;output trie&lt;/strong&gt;&lt;br/&gt;
ie. to serialize a trie. &lt;br/&gt;
⇒ use &lt;em&gt;preorder traversal&lt;/em&gt;: &lt;br/&gt;
0 for internal nodes, and 1 for leaf (followed by the corresponding char)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image004.png"/&gt;&lt;br/&gt;
recursive method:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;writeTrie&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;isLeaf&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;true&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // leaf node  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;ch&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // followed by the char  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;false&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // internal node  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;writeTrie&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;writeTrie&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;x&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;read trie&lt;/strong&gt;&lt;br/&gt;
Reconstruct the trie from the serialized bitstring. &lt;br/&gt;
preorder(x) = x+preorder(x.left)+preorder(x.right) ⇒ recursive method...   &lt;/p&gt;
&lt;p&gt;这个递归函数还是蛮有代表性的, 值得看.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readTrie&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;readBoolean&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;ch&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;readChar&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;ch&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readTrie&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;readTrie&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'\0'&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // subtle recursion  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="huffman-algorithm"&gt;Huffman algorithm&lt;/h3&gt;
&lt;p&gt;pb: how to find the best prefixless code?   &lt;/p&gt;
&lt;p&gt;Shannon-Fano algo:  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;partition symbols S into 2 subsets: S1, S0, with roughly equal freq  &lt;/li&gt;
&lt;li&gt;code in S1 start with 1 and in S0 start with 0  &lt;/li&gt;
&lt;li&gt;recur on S1 and S0  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;strong&gt;[Huffman algo]&lt;/strong&gt; (1950) &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;count letter freq in input  &lt;/li&gt;
&lt;li&gt;build a node for each char  &lt;/li&gt;
&lt;li&gt;select the 2 tries with minimum weight(freq), merge them, and put it back  &lt;/li&gt;
&lt;li&gt;repeat until we get only 1 trie  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;application: jpeg, pdf, mp3, ...  &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;implementation&lt;/strong&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;buildTrie&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'\0'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. Huffman algorithm produces the optimal prefixless code.   &lt;/p&gt;
&lt;p&gt;running time: &lt;strong&gt;N + RlgR&lt;/strong&gt; &lt;/p&gt;
&lt;h1 id="4-lzw-compression_1"&gt;4. LZW Compression&lt;/h1&gt;
&lt;p&gt;idea:&lt;br/&gt;
adaptive model: learn and &lt;em&gt;update&lt;/em&gt; the model as you read the text. &lt;br/&gt;
decoder will do the same thing.   &lt;/p&gt;
&lt;p&gt;build a table of not only mapping chars to codes, but also mapping &amp;gt;=2-char combinations to codes(of fixed width). &lt;br/&gt;
when encoding strings, look for the longest prefix that is in our table. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;h3 id="lzw-compression"&gt;LZW compression&lt;/h3&gt;
&lt;p&gt;LZW compression algo  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;create a symbol table mapping string keys to W-bit code, initialize as mapping only chars to codes  &lt;/li&gt;
&lt;li&gt;find longest prefix &lt;code&gt;s&lt;/code&gt; of the unscanned input   &lt;/li&gt;
&lt;li&gt;write out the corresponding code   &lt;/li&gt;
&lt;li&gt;add &lt;code&gt;s+c&lt;/code&gt; into the symbol table, where &lt;code&gt;c&lt;/code&gt; is the next char in input  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Use a trie for representing the code table → because support longest prefix match.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;implementation&lt;/strong&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;compress&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;TST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;st&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;TST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;; // a trie symbol table  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;; i&amp;lt;R; i++)  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;st&lt;/span&gt;.&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;""&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;char&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;code&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;R&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="c1"&gt;; // R is used as "stop"  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;st&lt;/span&gt;.&lt;span class="nv"&gt;longestPrefixOf&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;st&lt;/span&gt;.&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;W&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;())&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;st&lt;/span&gt;.&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;.&lt;span class="nv"&gt;charAt&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;code&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;input&lt;/span&gt;.&lt;span class="nv"&gt;substring&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;l&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;write&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;R&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;W&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // write "stop"  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;BinaryStdOut&lt;/span&gt;.&lt;span class="nv"&gt;close&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="lzw-expansion"&gt;LZW expansion&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;no need to get the codeword table&lt;/em&gt;, the input is just the compressed bitstring.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;maintain a (reverse)table mapping int(code) to strings.   &lt;/li&gt;
&lt;li&gt;as we decode the string, we add new entries to our table.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;to represent the table: just an array.   &lt;/p&gt;
&lt;p&gt;&lt;em&gt;note&lt;/em&gt; when add new entries: add key = &lt;code&gt;s+c&lt;/code&gt;, where &lt;code&gt;s&lt;/code&gt; is the last decoded string, &lt;code&gt;c&lt;/code&gt; is the first char of the currently decoded string.&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image008.png"/&gt;&lt;br/&gt;
example: when decoded ABR, s = BR, currently decoded string = ABR, so we add BRA.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;tricky case&lt;/strong&gt;: ABABABA&lt;br/&gt;
compression&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image009.png"/&gt;&lt;br/&gt;
problem in expansion when reading the "83": &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;p&gt;→ need to be able to update the table when encountering a code not yet defined...   &lt;/p&gt;
&lt;h1 id="summary_1"&gt;Summary&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;Huffman: fixed-length symbols, with variable-length codes.   &lt;/li&gt;
&lt;li&gt;LZW: variable-length symbols, with fixed-length codes.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;theoretical limit: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_2/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;还剩下一周的内容, 可能要等到二月底考完以后有时间再看了, 现在先复习备考...&lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 5-1 Regular Expressions</title><link href="https://x-wei.github.io/notes/algoII_week5_1.html" rel="alternate"/><published>2015-12-27T00:00:00+01:00</published><updated>2015-12-27T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-12-27:/notes/algoII_week5_1.html</id><summary type="html">&lt;h1 id="1-regular-expressions"&gt;1. Regular Expressions&lt;/h1&gt;
&lt;p&gt;pb: pattern matching. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h3 id="regular-expression"&gt;regular expression&lt;/h3&gt;
&lt;p&gt;Is a notation to specify a set of strings. &lt;br/&gt;
basic operations:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;concatenation   &lt;/li&gt;
&lt;li&gt;or  &lt;/li&gt;
&lt;li&gt;closure: "0 or more appearances of chars"  &lt;/li&gt;
&lt;li&gt;parentheses  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image001.png"/&gt;&lt;br/&gt;
additional operations (&lt;em&gt;added for convinence&lt;/em&gt;):&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image002.png"/&gt;&lt;br/&gt;
ex. &lt;code&gt;[A-C]+&lt;/code&gt; is equivalent to &lt;code&gt;(A|B|C)(A|B|C)*&lt;/code&gt;.  &lt;/p&gt;
&lt;p&gt;吐槽名句: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-res-and-nfas_1"&gt;2 …&lt;/h1&gt;</summary><content type="html">&lt;h1 id="1-regular-expressions"&gt;1. Regular Expressions&lt;/h1&gt;
&lt;p&gt;pb: pattern matching. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h3 id="regular-expression"&gt;regular expression&lt;/h3&gt;
&lt;p&gt;Is a notation to specify a set of strings. &lt;br/&gt;
basic operations:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;concatenation   &lt;/li&gt;
&lt;li&gt;or  &lt;/li&gt;
&lt;li&gt;closure: "0 or more appearances of chars"  &lt;/li&gt;
&lt;li&gt;parentheses  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image001.png"/&gt;&lt;br/&gt;
additional operations (&lt;em&gt;added for convinence&lt;/em&gt;):&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image002.png"/&gt;&lt;br/&gt;
ex. &lt;code&gt;[A-C]+&lt;/code&gt; is equivalent to &lt;code&gt;(A|B|C)(A|B|C)*&lt;/code&gt;.  &lt;/p&gt;
&lt;p&gt;吐槽名句: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-res-and-nfas_1"&gt;2. REs and NFAs&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;duality&lt;/strong&gt; between RE and DFA:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;RE: to decribe a set of strings.  &lt;/li&gt;
&lt;li&gt;DFA: machine to ecognize whether a string is in a given set.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;[Kleene's therom]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;For any DFA, there exists a RE that describes the same set of strings;&lt;br/&gt;
For any RE, there exists a DFA that recognizes the same set of strings.  &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;h3 id="first-attempt-of-pattern-matching"&gt;first attempt of pattern matching&lt;/h3&gt;
&lt;p&gt;(Ken Tompson) same as KMP — no backup.&lt;br/&gt;
basic plan:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;construct the DFA  &lt;/li&gt;
&lt;li&gt;simulate the DFA with text   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;bad news: DFA may have exponential nb of states. &lt;br/&gt;
⇒ change to &lt;strong&gt;NFA&lt;/strong&gt; (nondeterministic finite automaton).  &lt;/p&gt;
&lt;h3 id="nfa"&gt;NFA&lt;/h3&gt;
&lt;blockquote&gt;&lt;/blockquote&gt;
&lt;ul&gt;
&lt;li&gt;put RE into parentheses  &lt;/li&gt;
&lt;li&gt;every &lt;em&gt;char&lt;/em&gt; as a state (start=0, success=M) — 这里和之前的DFA很不一样: 之前是每个transition(edge)关联一个char, 这里是每个状态(node)关联一个char.   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;epsilon-transition&lt;/strong&gt; (red links below): change of machine state &lt;em&gt;without scanning text&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;match-transition&lt;/strong&gt; (black links below): change state, but also have to scan next char in text, &lt;em&gt;match transition is added after each alphabetic char&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;success (accept) if &lt;em&gt;any sequence&lt;/em&gt; of transitions (after scanning all text) end at state-M.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;亦可理解为, DFA是每一条边对应一个可能的(字母表内的)char, 而NFA只有match-transition对应于pattern里的(alphabetic) char, 其他epsilon transition的边对应空字符串(也就是epsilon string). &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image005.png"/&gt;&lt;br/&gt;
example:&lt;br/&gt;
is "AAAABD" a match ?&lt;br/&gt;
→ yes. (和上一节substring的插图进行一下比对, 还是有很大不同)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;p&gt;pb: non-determinism&lt;br/&gt;
How to determine whether a string is a match of a NFA (ie. &lt;em&gt;how to select the right sequence&lt;/em&gt; of transition) ? &lt;br/&gt;
⇒ sysematically  consider &lt;em&gt;all&lt;/em&gt; possible transition sequences.   &lt;/p&gt;
&lt;h1 id="3-nfa-simulation_1"&gt;3. NFA Simulation&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;state names: 0 to M. (M+1 states in total, M=length of RE string).   &lt;/li&gt;
&lt;li&gt;match-transitions: store in array &lt;code&gt;re[]&lt;/code&gt; (the match transitions are naturally in order of the array).  &lt;/li&gt;
&lt;li&gt;epsilon -transitions: store in a digraph &lt;code&gt;G&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;idea:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;maintain a &lt;em&gt;set&lt;/em&gt; of all state that NFA could be in after reading first i chars in text.   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;at each iteration: check all reachable state wrt the transitions, then update reachable states. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h3 id="algorithm"&gt;algorithm&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image008.png"/&gt;&lt;br/&gt;
(for the NFA above, 注意为了方便已经加了 必要的括号)  &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[Algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;initial: &lt;code&gt;rs&lt;/code&gt;(reachable state)=reachable state from state 0 (left parenthese) using epsilon trantisions   &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;consume a char &lt;em&gt;in text&lt;/em&gt;:   &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;nrs&lt;/code&gt; (&lt;em&gt;new-reachable-states&lt;/em&gt;) = empty set  &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;from all reachable state of this character: add next state using the match-transition to &lt;code&gt;nrs&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;add all reachable states (using epsilon transition) form the &lt;code&gt;nrs&lt;/code&gt; set to &lt;code&gt;nrs&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;set &lt;code&gt;rs = nrs&lt;/code&gt;, and consume the next char in text   &lt;/li&gt;
&lt;li&gt;accept if at the end the state M is in &lt;code&gt;rs&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;h3 id="concrete-example"&gt;concrete example&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;init:  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;when &lt;em&gt;matching A&lt;/em&gt; from text: state 2 or 6  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image011.png"/&gt;&lt;br/&gt;
using match transition of A, we can get to state 3 or 7&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image012.png"/&gt;&lt;br/&gt;
if we add epsilon transitions: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image013.png"/&gt;&lt;br/&gt;
so reachable states after reading 1st A are: 2, 3, 4, 7&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;matching 2nd A from text: state 2  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;using match transition we can only get to state 3. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image015.png"/&gt;&lt;br/&gt;
using epsilon transitions from state 3: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image016.png"/&gt;&lt;br/&gt;
 (&lt;em&gt;the only state after matching A is state 2 3 4&lt;/em&gt;)  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;etc...   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;或者直接看这张图:   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image017.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;h3 id="reachability"&gt;reachability&lt;/h3&gt;
&lt;p&gt;All reachable vertices from &lt;em&gt;a set of&lt;/em&gt; source vertices → just DFS. &lt;br/&gt;
⇒ directly use the API from the digraph section: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image019.png"/&gt;&lt;br/&gt;
running time linear to E+V  &lt;/p&gt;
&lt;h3 id="java-implementation"&gt;Java implementation&lt;/h3&gt;
&lt;p&gt;API:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;NFA&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kt"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;char&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="c1"&gt;// digraph of the epsilon-transitions  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;NFA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;toCharArray&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;buildEpsilonTransitionGraph&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="c1"&gt;// helper function to build the graph G  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;matches&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="c1"&gt;// does text match the regexp?  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;buildEpsilonTransitionGraph&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="c1"&gt;// private helper function  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;The function &lt;code&gt;buildEpsilonTransitionGraph()&lt;/code&gt;will be attacked in next session, for now we focus on the NFA simulation code — that is, the &lt;code&gt;mathes()&lt;/code&gt; method.   &lt;/p&gt;
&lt;p&gt;For simplicity let's assume we have a function &lt;code&gt;reachableVertices(Digraph G, Bag&amp;lt;Integer&amp;gt; sourceSet)&lt;/code&gt; and  &lt;code&gt;reachableVertices(Digraph G, int source)&lt;/code&gt; that gives the reachable states from (a set of) source vertices, including the sources. Or we can directly use the &lt;code&gt;DirectedDFS&lt;/code&gt; api as listed above.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;matches&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;text&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;does&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;text&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;match&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="vm"&gt;?&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;rechableStates&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reachableVertices&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;init&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reachable&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;c&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;text&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;newRechableStatesBymatch&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;i&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;rechableStates&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;||&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'.'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="n"&gt;newRechableStatesBymatch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;match&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;transition&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;rechableStates&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reachableVertices&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;newRechableStates&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;epsilon&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;transition&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reachableStates&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;(代码虽然短但是这个过程我理解了好久.. 另外上面的代码有点伪).   &lt;/p&gt;
&lt;h3 id="analysis"&gt;Analysis&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. the matches() method takes &lt;code&gt;O(MN)&lt;/code&gt; time in worst case.   &lt;/p&gt;
&lt;p&gt;pf. N chars in text, each char can go through &amp;lt;= M states (DFS), and in the digraph, no node has &amp;gt;3 degree ⇒ &lt;em&gt;number of edges &amp;lt;= 3M&lt;/em&gt;, so the time for each dfs is O(M), in total we have O(MN).   &lt;/p&gt;
&lt;h1 id="4-nfa-construction_1"&gt;4. NFA Construction&lt;/h1&gt;
&lt;p&gt;→ construct the epsilon transition digraph.   &lt;/p&gt;
&lt;h3 id="buiding-a-nfa-from-a-re-parsing"&gt;buiding a NFA from a re (parsing)&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;states in a NFA: one state per char, plus an  accept state (state M)  &lt;/li&gt;
&lt;li&gt;alphabet state: chars in alphabet (&lt;code&gt;A, B, C, D&lt;/code&gt;)  → (implicitly) put a match transition to next state  &lt;/li&gt;
&lt;li&gt;metacharacters:  &lt;code&gt;( ) . * |&lt;/code&gt; , 5 metacharacters in total  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ to deal with the metacharacters:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;paretheses &lt;/strong&gt;&lt;code&gt;( )&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;simply put a epsilon-transition to the next state&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image020.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;closure &lt;/strong&gt;&lt;code&gt;*&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;星号前面只可能是字母(包括&lt;code&gt;.&lt;/code&gt;)或者右括号&lt;code&gt;)&lt;/code&gt;, 所以分两种情况讨论一下, 需要向前看一位, 这里就比较subtle&lt;br/&gt;
for each &lt;code&gt;*&lt;/code&gt; state, add 3 transitions as below: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image021.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image022.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;or&lt;/strong&gt; &lt;code&gt;|&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;or符号肯定在一个括号里面&lt;br/&gt;
add 2 epsilon transitions wrt parethese: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image023.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image024.png"/&gt; &lt;/p&gt;
&lt;p&gt;以上就是NFA建立G的时候要处理的三种情形, 这三种情形都要知道一个左括号(&lt;code&gt;lp&lt;/code&gt;)的位置 ⇒ use a stack !   &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image025.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;for alphabetic chars: do one-char &lt;em&gt;lookahead&lt;/em&gt; → if next is &lt;code&gt;*&lt;/code&gt;, add transitions.   &lt;/li&gt;
&lt;li&gt;for left parenthese &lt;code&gt;(&lt;/code&gt;: add transition to next state, and push to stack  &lt;/li&gt;
&lt;li&gt;for or &lt;code&gt;|&lt;/code&gt;: add transition to next state, and push to stack   &lt;/li&gt;
&lt;li&gt;for right parenthese &lt;code&gt;)&lt;/code&gt;: pop the stack to deal with or and lp; and also do lookahead.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;code is not trival... look carefully:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;buildEpsilonTransitionGraph&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;helper&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;function&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stk&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'|'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;||&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'('&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;stk&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'('&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;||&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;')'&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;||&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'*'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;')'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;need&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;until&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stk&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'|'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stk&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;or&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;or&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="ow"&gt;or&lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;case&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="ow"&gt;or&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;do&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;lookahead&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;'*'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="s1"&gt;')'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;closure&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;rp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;before&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lp&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;closure&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;an&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;alphabetic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;before&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;go&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;through&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="analysis_1"&gt;Analysis&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. building an NFA takes linear time and space in M. &lt;br/&gt;
pf. for each char, the nb of operations is const.   &lt;/p&gt;
&lt;p&gt;真不愧是most ingenius algorithm we met in this course......   &lt;/p&gt;
&lt;h1 id="5-regular-expression-applications_1"&gt;5. Regular Expression Applications&lt;/h1&gt;
&lt;h3 id="grep"&gt;grep&lt;/h3&gt;
&lt;p&gt;"&lt;strong&gt;G&lt;/strong&gt;eneralized &lt;strong&gt;R&lt;/strong&gt;egular &lt;strong&gt;E&lt;/strong&gt;xpression &lt;strong&gt;P&lt;/strong&gt;rint"&lt;br/&gt;
print out all lines (from stdin) having a substring of an RE.&lt;br/&gt;
⇒ equal to adding a &lt;code&gt;.*&lt;/code&gt; to the beginning and end of the RE to make a match.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class GREP{  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    public void main(String[] args){  &lt;/span&gt;
&lt;span class="code-line"&gt;        String re = ".*"+args[0]+".*";  &lt;/span&gt;
&lt;span class="code-line"&gt;        NFA nfa = new NFA(re);  &lt;/span&gt;
&lt;span class="code-line"&gt;        while(StdIn.hasNextLine){  &lt;/span&gt;
&lt;span class="code-line"&gt;            String line = StdIn.readLine();  &lt;/span&gt;
&lt;span class="code-line"&gt;            if(nfa.matches(line)) StdOut.println(line);  &lt;/span&gt;
&lt;span class="code-line"&gt;        }  &lt;/span&gt;
&lt;span class="code-line"&gt;    }  &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;the grep has NM worst case running time — same as brute force substring search — amazing...  &lt;/p&gt;
&lt;p&gt;grep application: crossword puzzles&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image026.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image027.png"/&gt; &lt;/p&gt;
&lt;h3 id="regexp-in-other-languages"&gt;regexp in other languages&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;unix: grep, awk  &lt;/li&gt;
&lt;li&gt;script: python, &lt;em&gt;perl&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image028.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;java: &lt;code&gt;String.matches(regexp)&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image029.png"/&gt; &lt;/p&gt;
&lt;h3 id="harvesting-information"&gt;Harvesting information&lt;/h3&gt;
&lt;p&gt;goal: print &lt;em&gt;all substrings&lt;/em&gt; of input that match an RE. &lt;br/&gt;
use &lt;code&gt;Pattern&lt;/code&gt; and &lt;code&gt;Matcher&lt;/code&gt; class in &lt;code&gt;java.util.regexp&lt;/code&gt;. &lt;br/&gt;
first compile the regexp, then build the matcher&lt;br/&gt;
→ so that we can iterate through all matches of the input using &lt;code&gt;find()&lt;/code&gt; and &lt;code&gt;group()&lt;/code&gt; of the matcher &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image030.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;em&gt;Caveat&lt;/em&gt;: performance NOT guaranteed ! &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image031.png"/&gt;&lt;br/&gt;
→ exponential time growth! &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image032.png"/&gt; &lt;/p&gt;
&lt;h3 id="not-so-regular-expressions"&gt;Not-so-regular expressions&lt;/h3&gt;
&lt;p&gt;"not rugular" means Kleene's Th doesn't hold &lt;br/&gt;
→ efficient performance not tractable......&lt;br/&gt;
&lt;strong&gt;back-reference&lt;/strong&gt;&lt;br/&gt;
&lt;code&gt;\1&lt;/code&gt; matches &lt;em&gt;subexpressions&lt;/em&gt; that was matched earliser&lt;br/&gt;
limitations of regular languages: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image034.png"/&gt; &lt;/p&gt;
&lt;h3 id="summary"&gt;Summary&lt;/h3&gt;
&lt;p&gt;the substring and regexp are examples of compilers ! (from string to a NFA/DFA/bytecode)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image033.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week5_1/pasted_image035.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>Priority Queue/Heap (优先队列/堆)小结</title><link href="https://x-wei.github.io/tech/heap-summary.html" rel="alternate"/><published>2015-12-09T00:00:00+01:00</published><updated>2015-12-09T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-12-09:/tech/heap-summary.html</id><summary type="html">&lt;p&gt;今天简单介绍一下优先队列(priority queue, 以下简称PQ)这个数据结构的实现.  &lt;/p&gt;
&lt;p&gt;PQ又叫"堆"(heap), 但是可能优先队列这个名字更容易记忆它的 …&lt;/p&gt;</summary><content type="html">&lt;p&gt;今天简单介绍一下优先队列(priority queue, 以下简称PQ)这个数据结构的实现.  &lt;/p&gt;
&lt;p&gt;PQ又叫"堆"(heap), 但是可能优先队列这个名字更容易记忆它的用途: pq是一种队列, 不过不是先进先出(FIFO), 而是每次出队的元素永远是优先级最高的.   &lt;/p&gt;
&lt;h1 id="logical-structure-of-pq"&gt;logical structure of PQ&lt;/h1&gt;
&lt;p&gt;个人感觉"堆"这个名字大概源于PQ的(逻辑上的)形状吧: PQ是一种树(tree), 准确的说, 是一种二叉树(binary tree), 说得再准确一点, 它是一种&lt;strong&gt;完全二叉树(complete binary tree)&lt;/strong&gt;: 没错, PQ是一种满足某些条件的完全二叉树.   &lt;/p&gt;
&lt;p&gt;所谓的"完全二叉树", 要满足:  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;除了最后一层, 所有层都排满(没有非空节点)  &lt;/li&gt;
&lt;li&gt;最后一层的所有非空节点都排在左边  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;一张图可以直观说明, 完全二叉树其实就是长得像这样:&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/heap-summary/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;一个完全二叉树能被成为PQ的话, 要满足的条件就是:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;对于任何一个节点, 它的优先级都大于左右子节点的优先级.   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;比如下图(圆圈里数字代表优先级):&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/heap-summary/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;这样看上去的话, 确实像是"一堆"东西的形状(码的还挺整齐的), 而且我们知道在这一堆节点里, 优先级最高的就是最顶上的那个节点了.   &lt;/p&gt;
&lt;p&gt;我很喜欢这个比喻: 一个heap就像是一个&lt;em&gt;公司的hirachy结构:&lt;/em&gt; 子节点就是下属, 父节点就是上司, 每一个上司的能力都比他的下属强(优先级比子节点搞). 能力最强(优先级最高)的人在最上面.  &lt;/p&gt;
&lt;h1 id="array-representation-of-pq"&gt;array representation of PQ&lt;/h1&gt;
&lt;p&gt;对于一个完全二叉树, 没有必要用常规的树结构(使用指针)来表示, 因为如果从上到下走过每层(每层内从左到右)给所有节点编号(根节点的编号为1)的话, 完全二叉树有以下性质:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;father(i) = i/2&lt;/code&gt; 其中father(i)表示编号为i的节点的父节点的下标   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;leftchild(i) = i*2, rightchild(i) = i*2+1&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;既然用数组表示的时候, 任何节点的父亲节点和左右子节点都可以轻松得到, 就没有必要使用指针了. 所以只需要一个数组即可表示PQ ! 比如一个int的PQ在内部只要表示为: &lt;code&gt;int pq[]&lt;/code&gt;.   &lt;/p&gt;
&lt;p&gt;另外注意, 上面的公式成立的前提是数组下标从1开始, 实现的时候我们把数组的第0个元素空出来即可.   &lt;/p&gt;
&lt;p&gt;不难看出一个PQ有以下性质:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;高度为lgN  &lt;/li&gt;
&lt;li&gt;第k层有 2^k 个节点 (root是第0层)  &lt;/li&gt;
&lt;li&gt;最后一层的节点对应的下标&amp;gt;=N/2  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;h1 id="pq-implementation"&gt;PQ implementation&lt;/h1&gt;
&lt;p&gt;先写一下代码框架:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;PQ&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;maxPQ&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;integers&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MAX_CAPACITY&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1000&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ArrayList&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;do&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;need&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MAX_CAPACITY&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;size&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rightmost&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;level&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;PQ&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;MAX_CAPACITY+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;assert&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;PQ&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;--&amp;gt; stay tuned  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;poll&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;remove&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;--&amp;gt; stay tuned  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;最关键的两个函数是&lt;code&gt;add&lt;/code&gt;和&lt;code&gt;poll&lt;/code&gt;, 实现这两个操作的关键在于两个基本操作: &lt;code&gt;siftup()&lt;/code&gt;和&lt;code&gt;siftdown()&lt;/code&gt;. 在PQ的性质被扰乱的时候, 使用这两个操作可以使PQ恢复性质(所谓的"调整").   &lt;/p&gt;
&lt;h3 id="siftup"&gt;siftup&lt;/h3&gt;
&lt;p&gt;如果一个新元素到来, 首先将其放在最后(最底层最右边的节点), 如果新来节点的优先级比较高, 可以用siftup将其提升到一个合适的层次. 用公司结构来类比就是新入职的员工由于能力强被提高到了高层, 而提升的办法就是: 和上司交换岗位(也就是和父节点交换位置).   &lt;/p&gt;
&lt;p&gt;所以这个操作只要不断把该元素与父节点交换, 直到遇到一个优先级大于该节点的父节点或者已经到了最高处停止. 代码很短:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;siftup&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;newly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;added&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i/2&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;/=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="siftdown"&gt;siftdown&lt;/h3&gt;
&lt;p&gt;siftdown的功能和siftup相反: 如果在最高处是一个优先级很低的元素, 需要将其"下放". 方法就是把它和子节点里面优先级较高的进行交换.   &lt;/p&gt;
&lt;p&gt;代码也不长, 不过第一次写可能不太简洁:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;siftdown&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nothing&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sift&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;when&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;empty&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;siftdown&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;level&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;element&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i*2&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;child&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i*2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i*2+1&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i*2+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stop&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;when&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bigger&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;than&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;both&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;child&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="implementation-of-add-and-poll_1"&gt;implementation of add and poll&lt;/h2&gt;
&lt;p&gt;有了这两个sift的基本操作, add和poll的操作就简单了. &lt;br/&gt;
&lt;strong&gt;add&lt;/strong&gt;&lt;br/&gt;
加入新元素的时候, 只要先把它放在最后面, 然后调用siftup()函数调整一下pq即可:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public void add(int n){ // insert element to PQ  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    assert size+1&amp;lt;MAX_CAPACITY;  &lt;/span&gt;
&lt;span class="code-line"&gt;    pq[++size] = n;  &lt;/span&gt;
&lt;span class="code-line"&gt;    siftup();  &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;poll&lt;/strong&gt;&lt;br/&gt;
堆顶元素被拿走以后, 我们可以先把最后一个元素放在顶部, 然后调用siftdown进行调整:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;poll&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;remove&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;top&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;element&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;assert&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nv"&gt;isEmpty&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;top&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;pq&lt;/span&gt;[&lt;span class="mi"&gt;1&lt;/span&gt;]&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;pq&lt;/span&gt;[&lt;span class="mi"&gt;1&lt;/span&gt;]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;pq&lt;/span&gt;[&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;]&lt;span class="c1"&gt;;// put last element on the top  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;siftdown&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;top&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="pq-application_1"&gt;PQ application&lt;/h1&gt;
&lt;p&gt;接下来讲一下PQ的应用.   &lt;/p&gt;
&lt;h3 id="heapsort"&gt;heapsort&lt;/h3&gt;
&lt;p&gt;由于每次出队的都是在剩下元素里面最大(小)的, 所以只要把数组的元素放到一个pq里, 然后依次poll出来, 得到的序列就是排序好了的.   &lt;/p&gt;
&lt;p&gt;不管是插入还是删除操作, 每次调整的复杂度为log(n) (堆的高度), 所以算法复杂度为 O(NlgN). 实际使用的时候效率比快速排序/合并排序略差, 以后专门写一篇关于排序算法的文章时再聊.   &lt;/p&gt;
&lt;h3 id="heapify"&gt;heapify&lt;/h3&gt;
&lt;p&gt;首先前面的siftdown函数很明显可以修改一下加上一个参数变为&lt;code&gt;siftdown(int i)&lt;/code&gt;(i代表要向下调整的元素的下标).   &lt;/p&gt;
&lt;p&gt;在heapsort里第一步是要建立一个PQ. 最naive的建堆操作就是新建一个空的heap然后不断向里面加入数组&lt;code&gt;a&lt;/code&gt;里的元素(空间复杂度N, 时间复杂度NlgN). 其实这个操作可以做的更好: 我们&lt;em&gt;先直接把数组a当作pq[]数组&lt;/em&gt;, 现在显然它不满足PQ性质, 只需要&lt;em&gt;多次使用siftdown&lt;/em&gt;进行调整即可.   &lt;/p&gt;
&lt;p&gt;假设一共有h(=lgN)层, 由于最后一层的节点不必调用siftdown, 我们只要从倒数第二层开始调用siftdown即可, 结合前面提到的pq的性质(N/2以后的节点都在最后一层), 写法很简单(简单起见认为a也是把第0个元素空出来好了):   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;heapify&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="c1"&gt;;i&amp;lt;=1;i--){  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;siftdown&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这个操作的时间复杂度是O(N)的 ! 为什么呢?&lt;br/&gt;
→ 第k层节点有2^k个节点, 这一层的节点向下调整最多会进行h-k步, 所以计算量是一个求和表达式: &lt;br/&gt;
&lt;code&gt;Sigma( 2^k * (h-k) ) for k=0,...,h-1&lt;/code&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/heap-summary/pasted_image002.png"/&gt;&lt;br/&gt;
(具体见 &lt;a href="http://algs4.cs.princeton.edu/24pq/"&gt;http://algs4.cs.princeton.edu/24pq/&lt;/a&gt; 里面Q20的答案)  &lt;/p&gt;
&lt;h3 id="top-k-elements-of-a-stream"&gt;top K elements of a stream&lt;/h3&gt;
&lt;p&gt;问题描述: 一系列数字一个一个到达, 当所有数(假设有N个)都到达以后, 求最大的K个数字.   &lt;/p&gt;
&lt;p&gt;这是一个经典的PQ应用 ⇒ 使用一个最小堆(minPQ)即可达到这个效果: 新建一个minPQ(最小的数字在最上面, 每次当一个数字n到达时:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if minPQ.size&amp;lt;K → &lt;code&gt;minPQ.add(n)&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;if minPQ.size==K → 比较n和minPQ.top():   &lt;ul&gt;
&lt;li&gt;if n&amp;gt;minPQ.top(): &lt;code&gt;minPQ.poll(); minPQ.add(n)&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;else pass...  &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="median-of-a-stream"&gt;median of a stream&lt;/h3&gt;
&lt;p&gt;问题描述: 一系列数字一个一个到达, 求他们的中位数(median)?&lt;br/&gt;
这个的解法是使用&lt;em&gt;两个PQ&lt;/em&gt;, 一个最大堆&lt;code&gt;maxpq&lt;/code&gt;一个最小堆&lt;code&gt;minpq&lt;/code&gt;, 然后&lt;em&gt;maxpq里存放较&lt;/em&gt;&lt;strong&gt;小&lt;/strong&gt;&lt;em&gt;的一半数字, minpq里存放较&lt;/em&gt;&lt;strong&gt;大&lt;/strong&gt;&lt;em&gt;的一半数字: &lt;/em&gt;&lt;code&gt;maxpq.top()&amp;lt;=minpq.top()&lt;/code&gt;. &lt;br/&gt;
并且我们要求: &lt;code&gt;minpq.size &amp;lt;= maxpq.size &amp;lt;= minpq.size+1&lt;/code&gt;&lt;br/&gt;
⇒ 这样中位数或者是maxpq.top(), 或者是两个top的平均值了~  &lt;/p&gt;
&lt;p&gt;初始时两个pq都是空的, 每次数字n到来时:&lt;br/&gt;
&lt;em&gt; 先把n放进maxpq里&lt;br/&gt;
&lt;/em&gt; 如果&lt;code&gt;maxpq.size&amp;gt;minpq.size+1&lt;/code&gt;的话: &lt;code&gt;minpq.add(maxpq.poll())&lt;/code&gt; &lt;/p&gt;
&lt;h1 id="more-about-heap_1"&gt;more about heap&lt;/h1&gt;
&lt;h3 id="k-way-heap"&gt;k-way heap&lt;/h3&gt;
&lt;p&gt;这里介绍的PQ其实是binary heap, 即这棵树是一个完全&lt;strong&gt;二&lt;/strong&gt;叉树, 但是我们完全可以做成完全&lt;strong&gt;K&lt;/strong&gt;叉树, 就是所谓的K-way heap了.  &lt;/p&gt;
&lt;p&gt;这样的好处是heap的高度会变得更小(从log2(N)变为logK(N)), 不过由于每个分叉变成了K个, 所以siftdown每次循环的操作复杂度也会增加(从2变为K).   &lt;/p&gt;
&lt;h3 id="more-flexible-heap"&gt;more "flexible" heap&lt;/h3&gt;
&lt;p&gt;在某些应用中(比如Dijkstra算法), 我们希望在插入后修改某个元素的优先级, 这时候需要对这个标准的heap做一些修改, 需要用一个数组把元素的"逻辑编号"和在pq数组里的"实际编号"相互转换.   &lt;/p&gt;
&lt;p&gt;不过这个会比较subtle(其实我已经记不起来了...), 见: &lt;a href="http://x-wei.github.io/algoII_week2_2.html"&gt;http://x-wei.github.io/algoII_week2_2.html&lt;/a&gt; (IndexedPQ部分)&lt;/p&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 4-2 Substring Search</title><link href="https://x-wei.github.io/notes/algoII_week4_2.html" rel="alternate"/><published>2015-12-07T00:00:00+01:00</published><updated>2015-12-07T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-12-07:/notes/algoII_week4_2.html</id><summary type="html">&lt;h1 id="1-introduction-to-substring-search"&gt;1. Introduction to substring search&lt;/h1&gt;
&lt;p&gt;"most ingenious algorithm we've seen so far"&lt;br/&gt;
&lt;strong&gt;pb. &lt;/strong&gt;having two strings, &lt;code&gt;pattern&lt;/code&gt; and &lt;code&gt;text&lt;/code&gt;, len(pattern)=M &amp;lt;&amp;lt; len(text)=N, try to find pattern in text.   &lt;/p&gt;
&lt;p&gt;ex. &lt;code&gt;indexOf&lt;/code&gt; method of String in java.   &lt;/p&gt;
&lt;h1 id="2-brute-force-substring-search"&gt;2. Brute-Force Substring Search&lt;/h1&gt;
&lt;p&gt;function signature: &lt;br/&gt;
&lt;code&gt;public static int search(String pat …&lt;/code&gt;&lt;/p&gt;</summary><content type="html">&lt;h1 id="1-introduction-to-substring-search"&gt;1. Introduction to substring search&lt;/h1&gt;
&lt;p&gt;"most ingenious algorithm we've seen so far"&lt;br/&gt;
&lt;strong&gt;pb. &lt;/strong&gt;having two strings, &lt;code&gt;pattern&lt;/code&gt; and &lt;code&gt;text&lt;/code&gt;, len(pattern)=M &amp;lt;&amp;lt; len(text)=N, try to find pattern in text.   &lt;/p&gt;
&lt;p&gt;ex. &lt;code&gt;indexOf&lt;/code&gt; method of String in java.   &lt;/p&gt;
&lt;h1 id="2-brute-force-substring-search"&gt;2. Brute-Force Substring Search&lt;/h1&gt;
&lt;p&gt;function signature: &lt;br/&gt;
&lt;code&gt;public static int search(String pat, String txt);&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;brute-force algo: look for &lt;code&gt;pattern&lt;/code&gt; at every position of &lt;code&gt;text&lt;/code&gt;.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;search&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;pat&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;txt&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;txt&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;pat&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;; i&amp;lt;=N-M; i++){  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;; j&amp;lt;M &amp;amp;&amp;amp; pat.charAt(j)==txt.charAt(i+j); j++);  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="c1"&gt;;// not found  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;worst case: &lt;/strong&gt;when txt/pat are repetitive → MN compares. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image.png"/&gt;&lt;br/&gt;
problem with brute-force: always &lt;em&gt;backup&lt;/em&gt; when mismatch. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image001.png"/&gt;&lt;br/&gt;
&lt;strong&gt;brute-force alternative&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;j := number of matched chars in pattern  &lt;/li&gt;
&lt;li&gt;i := index of the end of matched char in text  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ do explicite backup when mismatch by &lt;code&gt;i -= j&lt;/code&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;search&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;pat&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;txt&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;txt&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;pat&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;pat&lt;/span&gt;.&lt;span class="nv"&gt;charAt&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;txt&lt;/span&gt;.&lt;span class="nv"&gt;charAt&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="ss"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;{&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="c1"&gt;; j++;}  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;{&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="c1"&gt;; j=0}// &amp;lt;==backup  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;?&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;:&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;challenge: want linear-time guarantee, and want to avoid backup.   &lt;/p&gt;
&lt;h1 id="3-knuth-morris-pratt"&gt;3. Knuth-Morris-Pratt&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;"one of the coolest/trickiest algorithm covered in this course"&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="intuition"&gt;intuition&lt;/h3&gt;
&lt;p&gt;suppose pattern = "BAAAAA", &lt;br/&gt;
if we matched 5 chars in pattern and get mismatch on 6th char ⇒ we know the previous 5 chars are "BAAAA"  → no need to backup the i pointer.   &lt;/p&gt;
&lt;p&gt;KMP algorithm: clever method that &lt;em&gt;always&lt;/em&gt; avoid backup !  &lt;/p&gt;
&lt;h3 id="deterministic-finite-state-automaton-dfa"&gt;Deterministic finite state automaton (DFA)&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;finite states ,including start and halt state, indexed by j in the subtring pb  &lt;/li&gt;
&lt;li&gt;for each state: exactly one transition for each char in alphabet  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex. &lt;br/&gt;
states are 0~6, pat="ABABAC", transitions are indexed by chars in alphabet = {A,B,C}, finish if we reach state-6.   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;code&gt;dfa[c][i]&lt;/code&gt; = the next state if we are currently in state-i and encoutered char-c.  &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;interpretation of DFA for KMP algo&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;in the DFA after reading &lt;code&gt;txt[i]&lt;/code&gt;, the index of state is the &lt;strong&gt;number of matched chars&lt;/strong&gt; in pattern, or length of *longest prefix of pat that is a suffix of txt[0:i]. *  &lt;/p&gt;
&lt;/blockquote&gt;
&lt;ul&gt;
&lt;li&gt;need to precompute the &lt;code&gt;dfa[][]&lt;/code&gt; array from pattern  &lt;/li&gt;
&lt;li&gt;the pointer i &lt;em&gt;never&lt;/em&gt; decrements (thus we can do it in a &lt;em&gt;streaming&lt;/em&gt; manner)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ &lt;em&gt;if&lt;/em&gt; &lt;code&gt;dfa[][]&lt;/code&gt; &lt;em&gt;is precomputed&lt;/em&gt;, java code is very very simple:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[][]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;txt.charAt(i)&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="vm"&gt;?&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;running time: linear.&lt;br/&gt;
→ key pb: &lt;em&gt;how to build dfa efficiently&lt;/em&gt; ?  &lt;/p&gt;
&lt;h3 id="dfa-construction"&gt;DFA construction&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;match transition &lt;/strong&gt;(easy part)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;when at state j, for the char &lt;code&gt;c0==pat.charAt(j+1)&lt;/code&gt;, just go on matching: &lt;code&gt;dfa[c0][j] = j+1&lt;/code&gt;&lt;br/&gt;
ex. (&lt;em&gt;pat="ABABAC"&lt;/em&gt;)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image003.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;mismatch transition&lt;/strong&gt; (hard part)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(for j==0, things are simple: &lt;code&gt;dfa[c][0]=0&lt;/code&gt; for all &lt;code&gt;c!=pat[0]&lt;/code&gt;)  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;at state &lt;/em&gt;&lt;code&gt;j&lt;/code&gt; (ie. j chars in pattern are matched)&lt;em&gt;, and for &lt;/em&gt;&lt;code&gt;c!=pat.charAt(j+1)&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;⇒ we are in state j: we know &lt;em&gt;the &lt;/em&gt;&lt;strong&gt;last j chars in input&lt;/strong&gt;&lt;em&gt; are &lt;/em&gt;&lt;code&gt;pat[0...j-1]&lt;/code&gt;, &lt;em&gt;and followed by char =&lt;/em&gt; &lt;code&gt;c&lt;/code&gt;, so the last j+1 chars of input string is: &lt;code&gt;pat[0...j-1]+c&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;⇒ to compute dfa[c][j]: we can &lt;strong&gt;simulate as if we backup&lt;/strong&gt;&lt;em&gt;, ie. &lt;/em&gt;&lt;code&gt;i=i-j+1, j=0&lt;/code&gt;.   &lt;/li&gt;
&lt;li&gt;if we go back to set j=0, and set i = i-j+1, then i is pointing at &lt;code&gt;pat[1]&lt;/code&gt;, the text become &lt;code&gt;pat[1...j-1]+c&lt;/code&gt;. We then let this string go through our dfa, the state that it achieves is the value of &lt;code&gt;dfa[c][j]&lt;/code&gt;.   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;em&gt;here is&lt;/em&gt; &lt;em&gt;a concrete example:&lt;/em&gt; &lt;br/&gt;
pattern = &lt;code&gt;"ABABAC"&lt;/code&gt;, state &lt;code&gt;j=5&lt;/code&gt;, char &lt;code&gt;c='B&lt;/code&gt;'  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;we know the last 6 chars of the input = &lt;code&gt;pat[0...j-1]+c="ABABA"+"B"="ABABAB"&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;if we backup, i will point to pat[1], the string is just &lt;code&gt;pat[1...j-1]+c="BABAB"&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;we use the string "BABAB" as input and go through the partially constructed dfa, and see that we will reach state 4  &lt;/li&gt;
&lt;li&gt;so we know &lt;code&gt;dfa['B'][5]=4&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;similarly we can get &lt;code&gt;dfa['A'][5]=1&lt;/code&gt;, as indicated below: &lt;br/&gt;
(&lt;em&gt;pat="ABABAC"&lt;/em&gt;)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;one concern: seems this simulation needs &lt;code&gt;j&lt;/code&gt; steps ?&lt;br/&gt;
⇒ can be changed to be constant time if we maintain a &lt;strong&gt;state X := the state of simulating of input=pat[1...j-1]&lt;/strong&gt;&lt;br/&gt;
we maintain this state &lt;code&gt;X&lt;/code&gt;, then for each &lt;em&gt;mismatched&lt;/em&gt; char c, we just need to look at &lt;code&gt;dfa[c][X]&lt;/code&gt;. &lt;br/&gt;
(&lt;em&gt;pat="ABABAC"&lt;/em&gt;)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[Algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;set all matched transitions &lt;code&gt;dfa[c0][j] = j+1&lt;/code&gt; for all &lt;code&gt;c0==pat[j]&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;fill first column (j==0): &lt;code&gt;dfa[c][0]=0&lt;/code&gt; for all &lt;code&gt;c!=pat[0]&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;initialize &lt;code&gt;X=0&lt;/code&gt; (state for empty input string)  &lt;/li&gt;
&lt;li&gt;for j=1 to M:  &lt;ul&gt;
&lt;li&gt;for all &lt;code&gt;c!=pat[0]&lt;/code&gt;: set &lt;code&gt;dfa[c][j] = dfa[c][X]&lt;/code&gt; (DP here...)  &lt;/li&gt;
&lt;li&gt;update &lt;code&gt;X=dfa[c0][X]&lt;/code&gt; ⇒ 注意, 此时X并&lt;strong&gt;不等于&lt;/strong&gt;X+1(最开始&lt;code&gt;dfa[c0][j]=j+1&lt;/code&gt;不适用于此), 为什么? 因为&lt;code&gt;c0==pat[j]&lt;/code&gt; 而不&lt;code&gt;是pat[X]&lt;/code&gt;!! 比如说最开始, j=1的时候X是等于0的!!! (这个弯我饶了好几分钟...)  &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;java code (can be written to be more compate):   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[][]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;constructDFA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;256&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nf"&gt;ASCII&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;code&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[][]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;1.&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fill&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;matched&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;transitions&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;pat.charAt(j)&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;pat.charAt(j)&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;2.&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fill&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;column&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;--&amp;gt; can be ignored as java int default val=0  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;3.&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fill&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mismatched&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;transitions&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;pat.charAt(j)&lt;/span&gt;&lt;span class="o"&gt;][&lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfa&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;running time and space: &lt;strong&gt;O(M*R)&lt;/strong&gt;.  &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;prop.&lt;/strong&gt; &lt;br/&gt;
KMP algorithm runs in O(M+N) time, and constructs the dfa in O(M*R) time/space.   &lt;/p&gt;
&lt;p&gt;这个KMP算法, 我曾经想过好几个小时, 然后最后写出了特别复杂的代码, 虽然可以用但是基本写了就忘掉了. 但是经过老爷子这么一讲, 感觉这次印象深刻了好多. 老爷子NB...  &lt;/p&gt;
&lt;p&gt;八卦时间: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-boyer-moore_1"&gt;4. Boyer-Moore&lt;/h1&gt;
&lt;p&gt;Heuristic in practice.&lt;br/&gt;
i does not necessarily go through all txt chars ⇒ i may &lt;em&gt;skip&lt;/em&gt; some chars.   &lt;/p&gt;
&lt;h3 id="intuition_1"&gt;intuition&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;for matching: scan chars &lt;em&gt;from right to left&lt;/em&gt; (j will decrease when checking)  &lt;/li&gt;
&lt;li&gt;when encoutered a mismatch: we can skip &amp;lt;= M chars (if the char is not in pattern)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex. (pat="NEEDLE")&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;p&gt;→ pb: how to skip?   &lt;/p&gt;
&lt;h3 id="mismatch-character-heuristic"&gt;mismatch character heuristic&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;note&lt;/em&gt;: the &lt;code&gt;i&lt;/code&gt; always points to the &lt;em&gt;beginning&lt;/em&gt; of the substring (&lt;code&gt;txt[i,...,i+M-1]&lt;/code&gt;) to be checked for match.  &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;case 1. mismatched char not in pattern&lt;/strong&gt;&lt;br/&gt;
easy case → just move i to the right of this char. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;case 2. mismatched char in pattern&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;heuristic:&lt;/strong&gt; line up i with the &lt;strong&gt;rightmost&lt;/strong&gt;&lt;em&gt; char in pattern&lt;/em&gt;.&lt;br/&gt;
&lt;code&gt;i += skip&lt;/code&gt;&lt;br/&gt;
where &lt;em&gt;skip length = j - index of rightmost char in pattern&lt;/em&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;p&gt;note: this does not always help, in the example below, i even &lt;em&gt;backups&lt;/em&gt;: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image011.png"/&gt;&lt;br/&gt;
to avoid backup, in this case we just &lt;em&gt;increment i by 1&lt;/em&gt; (heuristic doesn't help in this case).  &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;use an array &lt;code&gt;right[]&lt;/code&gt; as &lt;em&gt;skip table&lt;/em&gt;, &lt;code&gt;right[c]&lt;/code&gt; is the index of rightmost occurrence of char c (-1 if c not in pat). &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pattern&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;pat.charAt(j)&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;using this table we can implemente the heuristic algorithm:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kt"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kr"&gt;right&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;length&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;length&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kr"&gt;skip&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="kr"&gt;skip&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="kr"&gt;skip&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pat&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)){&lt;/span&gt;&lt;span class="c1"&gt;// when mismatch happens  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="kr"&gt;skip&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;max&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kr"&gt;right&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;txt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)]);&lt;/span&gt;&lt;span class="c1"&gt;// skip if we can, else just increment i by 1  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kr"&gt;skip&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;// if the above for loop finishes without changing skip --&amp;gt; we are done.    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="kr"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="kr"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="c1"&gt;// pattern not found  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="analysis"&gt;analysis&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;property&lt;/strong&gt;. the Boyer-Moore heuristic (in practice) takes about &lt;strong&gt;N/M&lt;/strong&gt; (sublinear!) compares to search.   &lt;/p&gt;
&lt;p&gt;好神奇, 比KMP还要简单的算法, 实际效率这么高...  &lt;/p&gt;
&lt;p&gt;worst-case performance: &lt;strong&gt;N*M&lt;/strong&gt;... 这一点不如KMP. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image013.png"/&gt;&lt;br/&gt;
→ can be improved...   &lt;/p&gt;
&lt;h1 id="5-rabin-karp_1"&gt;5. Rabin-Karp&lt;/h1&gt;
&lt;p&gt;两个图灵奖的大神发明的算法..   &lt;/p&gt;
&lt;h3 id="intuition_2"&gt;intuition&lt;/h3&gt;
&lt;p&gt;basic idea: &lt;strong&gt;modular hashing&lt;/strong&gt;&lt;br/&gt;
ex. for strings of numbers   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;compute hash fcn (for number strings is easy: take the string and treat it as a number, then %Q where Q is a big prime number).   &lt;/li&gt;
&lt;li&gt;for a pointer i →corresponds to the substring &lt;code&gt;txt[i, ..., i+M-1]&lt;/code&gt;  → check hash for match  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(below: text=3141592653589793, pattern=26535)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;h3 id="computing-the-hash-function-efficiently"&gt;computing the hash function efficiently&lt;/h3&gt;
&lt;p&gt;let ti be the ith char in txt, the hashcode for substring &lt;code&gt;txt[i,...,i+M-1]&lt;/code&gt; is: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image015.png"/&gt;&lt;br/&gt;
⇒ just an M-digit base-R integer modulo Q ! &lt;code&gt;poly(M, R) % Q&lt;/code&gt;*. *  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Honor's method&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;linear time algorithm for evaluating polynomial. &lt;br/&gt;
recursive equation: &lt;code&gt;poly(i, R) = poly(i-1, R)*R+ti&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;ex. (R=10, M=5)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;private long hash(String key, int M){  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    long h=0;  &lt;/span&gt;
&lt;span class="code-line"&gt;    for(int i=0;i&amp;lt;M;i++)  &lt;/span&gt;
&lt;span class="code-line"&gt;        h = ( h*R + key.charAt(i) ) % Q  &lt;/span&gt;
&lt;span class="code-line"&gt;    return h;  &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;if we know x_i, the x_i+1 can be infered:   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image017.png"/&gt;&lt;br/&gt;
⇒ x_i+1 can be computed in constant time: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image018.png"/&gt;&lt;br/&gt;
⇒ we precompute R^(M-1) and maintain the hash number, and check for match !   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public static int search(String txt, String pat){  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    int N=txt.length(), M=pat.length();  &lt;/span&gt;
&lt;span class="code-line"&gt;    long pathash = hash(pat, M);      &lt;/span&gt;
&lt;span class="code-line"&gt;    int RM = R^(M-1);// &amp;lt;-- pseudo code, store value of R^(M-1)  &lt;/span&gt;
&lt;span class="code-line"&gt;    long txthash = hash(txt, M);// txthash will be maintained  &lt;/span&gt;
&lt;span class="code-line"&gt;    for(int i=0;i&amp;lt;N-M;i++){  &lt;/span&gt;
&lt;span class="code-line"&gt;        if(txthash==pathash &amp;amp;&amp;amp; checkMatch(i,txt,pat))   &lt;/span&gt;
&lt;span class="code-line"&gt;            return i;  &lt;/span&gt;
&lt;span class="code-line"&gt;        txthash = ( (txthash - txt.charAt(i)*RM)*R + txt.charAt(i+M) ) % Q;  &lt;/span&gt;
&lt;span class="code-line"&gt;    }  &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;更新txthash的地方可能会有modulo造成的问题... 不过先这样写吧..   &lt;/p&gt;
&lt;p&gt;for collisions: &lt;em&gt;Monte Carlo&lt;/em&gt; vs. &lt;em&gt;Las Vegas&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="analysis_1"&gt;analysis&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;Theory&lt;/strong&gt;: if Q is sufficiently large (~M&lt;em&gt;N^2), the probability of collision is ~1/N. &lt;br/&gt;
&lt;/em&gt;&lt;em&gt;Practice&lt;/em&gt;*: choose Q to be sufficiently large, and collision probability is ~1/Q.   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image019.png"/&gt; &lt;/p&gt;
&lt;h1 id="summery_1"&gt;Summery&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_2/pasted_image020.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>quick sort and more: 快速排序算法总结</title><link href="https://x-wei.github.io/tech/quick-sort-and-more.html" rel="alternate"/><published>2015-12-07T00:00:00+01:00</published><updated>2015-12-07T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-12-07:/tech/quick-sort-and-more.html</id><summary type="html">&lt;p&gt;今天总结一下非常有用的快速排序(qsort)算法, 以及由此衍生的一些其他相关算法(Knuth shuffle, quick select, 3-way partition).   &lt;/p&gt;
&lt;p&gt;快速排序的算法可以用三 …&lt;/p&gt;</summary><content type="html">&lt;p&gt;今天总结一下非常有用的快速排序(qsort)算法, 以及由此衍生的一些其他相关算法(Knuth shuffle, quick select, 3-way partition).   &lt;/p&gt;
&lt;p&gt;快速排序的算法可以用三句话描述:&lt;br/&gt;
&lt;strong&gt;[Algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;选择基准项(pivot element, 一般取第一个元素为pivot)  &lt;/li&gt;
&lt;li&gt;把数组里所有小于pivot的移动到pivot左边, 大于pivot的移动到右边 ⇒ 此时pivot已经位于最终排序时的正确位置  &lt;/li&gt;
&lt;li&gt;对pivot左右两个数组分别递归进行快速排序  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;由以上描述可见, qsort是一个递归算法, 我们可以把它的函数声明写成: &lt;code&gt;void qsort(int[] a, int lo, int hi)&lt;/code&gt;, 表示排序a[lo, hi]之间(闭区间)的所有元素.   &lt;/p&gt;
&lt;h2 id="quick-partition"&gt;quick partition&lt;/h2&gt;
&lt;p&gt;由上面描述可以见, qsort最关键的是第二步: 把数组元素以pivot分为两部分. 这个操作就是quick partition.   &lt;/p&gt;
&lt;p&gt;函数声明为: &lt;code&gt;int partition(int[] a, int lo, int hi)&lt;/code&gt;, 该函数返回pivot(即subarray的第一个元素&lt;code&gt;a[lo]&lt;/code&gt;)所在的位置.   &lt;/p&gt;
&lt;p&gt;如果允许新建一个临时数组的话, 那么这个就不是什么问题, 但是为了节约空间占用, 现在需要直接修改(in-place)使得a[lo] 到, 而且希望可以用尽量少的交换(&lt;code&gt;swap(int[]a, int i, int j)&lt;/code&gt;)操作, 就不是很evident了.   &lt;/p&gt;
&lt;p&gt;这个函数的写法是用两个指针i和j分别从两端向中间走, 如果两个指针指向的元素一个小于pivot一个大于pivot那么就进行交换, 当两个指针碰面的时候结束(最后把pivot和指针元素交换). 请看下面这个萌萌的图(图片来自&amp;lt;&amp;lt;啊哈!算法&amp;gt;&amp;gt;): &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/quick-sort-and-more/pasted_image003.png"/&gt;&lt;br/&gt;
选取第一个元素(6)为pivot, 然后j向左走直到遇到一个小于pivot(6)的数停止, i向右走直到遇到一个大于pivot的数停止(&lt;em&gt;注意要让j先移动&lt;/em&gt;), 此时二者交换: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/quick-sort-and-more/pasted_image004.png"/&gt;&lt;br/&gt;
只要重复这个过程, 直到i&amp;gt;=j为止, 此时只要最后把pivot和j(&lt;em&gt;注意是j而不是i&lt;/em&gt;)指向的元素交换即可: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/quick-sort-and-more/pasted_image005.png"/&gt;&lt;br/&gt;
所以pivot的位置就是j, 函数返回j即可.    &lt;/p&gt;
&lt;p&gt;java实现:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;=&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;--);// move j to a point where a[j]&amp;lt;pivot  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;=&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;move&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;point&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;where&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;meets&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;--);  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这里有几点要注意的:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;让j先移动  &lt;/li&gt;
&lt;li&gt;最后pivot要和j交换而不是和i交换: 因为最后放在最左边的应该是一个小于pivot的数嘛  &lt;/li&gt;
&lt;li&gt;移动的时候别忘了需要加数组下标的边界检查(&lt;code&gt;i&amp;lt;=hi&lt;/code&gt;, &lt;code&gt;j&amp;gt;=lo&lt;/code&gt;)  &lt;/li&gt;
&lt;li&gt;partition()的复杂度是线性的&lt;strong&gt;O(n)&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="knuth-shuffle"&gt;Knuth shuffle&lt;/h2&gt;
&lt;p&gt;qsort之所以快, 是因为每次都能够按照pivot分为大致同样长度的两个子数组(所以每次子问题的规模除以二), 所以复杂度为&lt;strong&gt;O(NlogN)&lt;/strong&gt;. 最坏情况下, 如果每次两个子数组中可能有一个长度为0, 那么每次子问题的规模只减少了1, 所以复杂度变成了quadratic &lt;strong&gt;O(N2)&lt;/strong&gt;.  &lt;/p&gt;
&lt;p&gt;为了防止这种最坏情况的出现, 可以在一切开始之前把数组打乱顺序, 所以这一节讨论快速shuffle的算法. 最经典的就是Knuth的shuffle算法了, 算法很简答, 描述为: for(k=1 to n): 每次把第k个元素和前k个元素中的随机一个元素交换.  &lt;/p&gt;
&lt;p&gt;代码只有两行:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;shuffle&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;K&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;; K&amp;lt;a.length; K++)  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;swap&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;K&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Random&lt;/span&gt;.&lt;span class="nv"&gt;nextInt&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;K&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;))&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;关于算法的正确性, 其实只要证明"元素i在shuffle后最终位于位置i"的概率为1/N即可, 不难证明.   &lt;/p&gt;
&lt;h2 id="quick-sort"&gt;quick sort&lt;/h2&gt;
&lt;p&gt;好了 有了以上两个辅助函数就可以写qsort函数了:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;qsort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nv"&gt;recursive&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;helper&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;function&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;partition&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;qsort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;qsort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;p&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;qsort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;shuffle&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;qsort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;其实qsort的主体就是那个partition函数, 单独把partition列出来是因为它不止可以用在排序, 还可以用来做quick select, 见quick select节.    &lt;/p&gt;
&lt;h2 id="quick-select"&gt;quick select&lt;/h2&gt;
&lt;p&gt;&lt;em&gt;对于一个没有排序的数组, 如何快速找到它的中值(median)?&lt;/em&gt;&lt;br/&gt;
以上这个问题的答案就在&lt;code&gt;partition()&lt;/code&gt;函数.   &lt;/p&gt;
&lt;p&gt;之前说过, &lt;code&gt;partition()&lt;/code&gt;函数的返回值表示pivot在排序好的数组中的位置(rank), 这个消息非常有用: 中值只不过是rank等于长度除以2的元素而已.   &lt;/p&gt;
&lt;p&gt;为了寻找rank等于k的元素, 我们用partition函数可以每次把问题规模缩小: 如果partition()=p&lt;k, 如果p="" 那么pivot左边的subarray不必考虑,=""&gt;k那么右边subarray不用考虑, 如果数组事先shuffle过了的话, 问题规模每次缩小一半.   &lt;/k,&gt;&lt;/p&gt;
&lt;p&gt;定义一个函数, 寻找rank等于k的元素, 代码类似于二分查找:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;findKth&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;shuffle&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;该算法内层循环为O(hi-lo), 每次问题规模减少一半, 所以复杂度为N+N/2+N/4+...+1 = 2N, 复杂度为线性时间!  &lt;/p&gt;
&lt;h2 id="3-way-qsort"&gt;3-way qsort&lt;/h2&gt;
&lt;p&gt;qsort之前有个bug: 在数组里很多重复元素的时候, 效率会下降为O(N2). 原因是qsort没有好好处理重复元素的问题.   &lt;/p&gt;
&lt;p&gt;于是Dijkstra提出了一个&lt;strong&gt;3-way partition&lt;/strong&gt;的算法: 把数组分为三部分: 左边&lt;code&gt;[lo, lt)&lt;/code&gt;严格小于pivot, 中间&lt;code&gt;[lt, gt]&lt;/code&gt;等于pivot, 右边&lt;code&gt;(gt, hi]&lt;/code&gt;严格大于pivot.   &lt;/p&gt;
&lt;p&gt;算法初始化&lt;code&gt;lt=lo, gt=hi, i=lo&lt;/code&gt;, 用指针i向右扫描, [i,gt]为未处理到的部分. &lt;br/&gt;
算法很subtle, invariant是这样的:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;a[lo,lt-1] &amp;lt; pivot  &lt;/li&gt;
&lt;li&gt;a[lt, i-1] = pivot  &lt;/li&gt;
&lt;li&gt;a[i,gt] = unseen  &lt;/li&gt;
&lt;li&gt;a[gt+1, hi] &amp;gt; pivot  &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/quick-sort-and-more/pasted_image006.png"/&gt;&lt;br/&gt;
这个图很有助于写代码: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/quick-sort-and-more/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;qsort3way&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i,gt&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;unseen&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lt,i-1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;gt+1, hi&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="c1"&gt;--, i);  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo, lt-1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;swap&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;qsort3way&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;qsort3way&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;说它很subtle, 除了因为没有那个图我写不出来以外, 还有就是, 在把i和lt交换时, i可以increment (因为我们知道&lt;code&gt;a[lt]==pivot&lt;/code&gt;), 但是i和gt交换时, i&lt;strong&gt;不能&lt;/strong&gt;increment: 因为a[gt]不知道多大, 所以i位置要继续检查.   &lt;/p&gt;
&lt;p&gt;另外说一句, quicksort的思想在radix sort和trie里面也有闪现, 见我关于这两个主题的MOOC笔记...&lt;/p&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 4-1 Tries</title><link href="https://x-wei.github.io/notes/algoII_week4_1.html" rel="alternate"/><published>2015-12-05T00:00:00+01:00</published><updated>2015-12-05T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-12-05:/notes/algoII_week4_1.html</id><summary type="html">&lt;p&gt;More efficient version of symbol-table where the keys are strings.   &lt;/p&gt;
&lt;h1 id="1-r-way-tries"&gt;1. R-way Tries&lt;/h1&gt;
&lt;p&gt;Two implementations of symbol tables that we've seen: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image.png"/&gt;&lt;br/&gt;
when keys are strings:&lt;br/&gt;
(&lt;code&gt;L&lt;/code&gt;=string length, &lt;code&gt;N&lt;/code&gt;=number of strings, &lt;code&gt;R&lt;/code&gt;=radix)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;for string keys ⇒ do better by avoiding examing the entire key.  &lt;/p&gt;
&lt;p&gt;goal: faster than hashtable, more …&lt;/p&gt;</summary><content type="html">&lt;p&gt;More efficient version of symbol-table where the keys are strings.   &lt;/p&gt;
&lt;h1 id="1-r-way-tries"&gt;1. R-way Tries&lt;/h1&gt;
&lt;p&gt;Two implementations of symbol tables that we've seen: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image.png"/&gt;&lt;br/&gt;
when keys are strings:&lt;br/&gt;
(&lt;code&gt;L&lt;/code&gt;=string length, &lt;code&gt;N&lt;/code&gt;=number of strings, &lt;code&gt;R&lt;/code&gt;=radix)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;for string keys ⇒ do better by avoiding examing the entire key.  &lt;/p&gt;
&lt;p&gt;goal: faster than hashtable, more flexible than BST !  &lt;/p&gt;
&lt;h2 id="string-symbol-table-api"&gt;String Symbol Table API&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;StringST&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;V&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;span class="c1"&gt;// implements ST&amp;lt;String, V&amp;gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;V&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;val&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;V&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="r-way-tries"&gt;R-way tries&lt;/h2&gt;
&lt;p&gt;A trie is a tree where:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;except the root, each node store &lt;em&gt;characters&lt;/em&gt; (instead of string keys) — in fact the chars are stored in &lt;em&gt;links&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;each node has R children  &lt;/li&gt;
&lt;li&gt;store &lt;em&gt;value&lt;/em&gt; in node if the node corresponds to the&lt;em&gt; last char&lt;/em&gt; in key.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;example: (&lt;em&gt;a trie&lt;integer&gt;)&lt;/integer&gt;&lt;/em&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;search in a trie &lt;/strong&gt;&lt;code&gt;get()&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;hit&lt;/em&gt; if when search ends the node has a non-null value&lt;br/&gt;
&lt;em&gt;miss&lt;/em&gt; if reach a null link or have null value when search ends.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;insertion in a trie&lt;/strong&gt; &lt;code&gt;put()&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;follow the links as the chars indicate in the key&lt;br/&gt;
→ if meet null links: create new node&lt;br/&gt;
→ when reach last char in key: set the value of the node  &lt;/p&gt;
&lt;h2 id="java-implementation"&gt;Java implementation&lt;/h2&gt;
&lt;p&gt;trie node class:&lt;br/&gt;
in each node use an array of size R to store links...  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Object&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;because&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cannot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;create&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;arries&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;generic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;type&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;implicitly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;defined&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;by&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;link&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;另外关于为什么内部类Node声明为static, 参考这里: &lt;br/&gt;
&lt;a href="http://www.geeksforgeeks.org/static-class-in-java/"&gt;http://www.geeksforgeeks.org/static-class-in-java/&lt;/a&gt; &lt;/p&gt;
&lt;p&gt;implementation: use private recursive methods, 和BST的实现类似, 定义一个递归的private函数, 返回插入后的Node, 很有用.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;TrieST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;pirvate&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;256&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;ASCII&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Object&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;because&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cannot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;create&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;arries&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;generic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;type&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;implicitly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;defined&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;by&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;link&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;recursive&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;helper&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;method&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="err"&gt;`&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;returns&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;inserted&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;cast&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;back&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;returns&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;contains&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;delete node in trie:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;find the node and set the val to null  &lt;/li&gt;
&lt;li&gt;if a node has 0 links(leaf)  and val==null: delete it and recursivly go up.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h2 id="analysis"&gt;analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;time:&lt;/strong&gt;&lt;br/&gt;
search hit —  L nodes examined. &lt;br/&gt;
serach miss —  sublinear in L&lt;br/&gt;
&lt;strong&gt;space:&lt;/strong&gt; &lt;br/&gt;
each node has R links (possibly null) — &lt;em&gt;too much memory for large R&lt;/em&gt; !&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image004.png"/&gt;&lt;br/&gt;
&lt;strong&gt;Application&lt;/strong&gt;&lt;br/&gt;
interview question: data structure for spell checking.   &lt;/p&gt;
&lt;h1 id="2-ternary-search-tries_1"&gt;2. Ternary Search Tries&lt;/h1&gt;
&lt;p&gt;Solution to the memory issue of R-way tries —  much fewer null links. ternery=tuple of 3...&lt;br/&gt;
TST:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;store chars (and vals) &lt;em&gt;explicitly&lt;/em&gt; in nodes  &lt;/li&gt;
&lt;li&gt;each node has &lt;strong&gt;3&lt;/strong&gt; children:   &lt;ul&gt;
&lt;li&gt;&lt;em&gt;smaller, larger: &lt;/em&gt;TST that starts with char smaller/bigger than its char c.   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;equal: &lt;/em&gt;the TST with keys that &lt;strong&gt;starts with&lt;/strong&gt; this char c  &lt;/li&gt;
&lt;li&gt;(所以除了用smaller/larger连接的节点在Rway trie里属于同一层  &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image005.png"/&gt;&lt;br/&gt;
类似于3-way radix sort(同一篇paper里提出的), 有有点RBTree的意思...   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;searching&lt;/strong&gt; in TST: quite similar to BST search, will go down ("equal" or "middle") when the current node matchs current char...  &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;Node class:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;private class Node{  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    private Value val;  &lt;/span&gt;
&lt;span class="code-line"&gt;    private char c;// store char explicitly  &lt;/span&gt;
&lt;span class="code-line"&gt;    private Node left, mid, right;  &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;TST class (again use recursive helper functions)&lt;br/&gt;
有一种写BST代码的感觉, 另外由于这次char是显式存在node里, 代码反而更好理解了...  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;TST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;process&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;means&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;go&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;down&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;one&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;level&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;left&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;do&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;increment&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;current&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;matchd&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;left&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="hybrid-of-tst-and-rway-trie"&gt;Hybrid of TST and Rway trie&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;at root: do &lt;em&gt;R^2 branching&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;other nodes are TSTs   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h2 id="analysis_1"&gt;analysis&lt;/h2&gt;
&lt;p&gt;space cost: linear in N.&lt;br/&gt;
time: if keys arrive in rand order... (can use rotation to get worst-case guarantee..)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h2 id="hashing-vs-tst"&gt;Hashing vs. TST&lt;/h2&gt;
&lt;p&gt;Hashing:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;need to check entire key no matter hit or miss  &lt;/li&gt;
&lt;li&gt;performance relies on hash functions  &lt;/li&gt;
&lt;li&gt;donot support ordered operations  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;TST:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;examines just enough chars  &lt;/li&gt;
&lt;li&gt;support ordered operations  &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-character-based-operations_1"&gt;3. Character-Based Operations&lt;/h1&gt;
&lt;p&gt;some very useful char-based operations:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;prefix match&lt;/strong&gt; &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;wildcard match&lt;/strong&gt;: use a dot to represent any char  &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;longest prefix&lt;/strong&gt;: find the key that is the longest prefix of a string  &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="api"&gt;API&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class TrieST&amp;lt;Value&amp;gt;{  &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    // functions decalred before..  &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;String&amp;gt; keys;  &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;String&amp;gt; keysWithPrefix(String s);  &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;String&amp;gt; keysThatMatch(String s);  &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;String&amp;gt; longestPrefixOf(String s);&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="keys-ordered-iteration"&gt;keys(): ordered iteration&lt;/h2&gt;
&lt;p&gt;&lt;code&gt;keys()&lt;/code&gt;: just an inorder-traversal of the &lt;em&gt;Rway trie&lt;/em&gt; →dfs, + maintain the chars in the path (root to current node). &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;collect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;helper&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;fcn&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;collect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pathstr&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;enqueue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pathstr&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pathstr&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;string&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;collect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pathstr&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="prefix-match"&gt;prefix match&lt;/h2&gt;
&lt;p&gt;very useful: ex. autocomplete, search bar, ...&lt;br/&gt;
implementation⇒ just find the end of that prefix, then call &lt;code&gt;keys()&lt;/code&gt; on the &lt;em&gt;subtrie&lt;/em&gt;.&lt;br/&gt;
之前写的俩helper function这里发挥作用了:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;keysWithPrefix&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;prefix&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;subtrieRoot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;prefix&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;collect&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;subtrieRoot&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;prefix&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="c1"&gt;;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="longest-prefix"&gt;longest prefix&lt;/h2&gt;
&lt;p&gt;⇒ just do a search and keep track of the longest key that we encounterd.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;longestPrefixOf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;substring&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;current&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;longest&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;prefix&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="application-t9-texting"&gt;application: T9 texting&lt;/h3&gt;
&lt;p&gt;classique... G面试以及X的TP里都有涉及过...   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;first: generate all string combinations  &lt;/li&gt;
&lt;li&gt;second: call get() on the trie of dictionaries.  &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="other-variants_1"&gt;Other Variants&lt;/h2&gt;
&lt;h3 id="patricia-trie"&gt;Patricia trie&lt;/h3&gt;
&lt;p&gt;improvement: remove the one-eay branching (put &amp;gt;1 chars in a node).&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h3 id="suffix-tree"&gt;suffix tree&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;patricia tree of the suffix  &lt;/li&gt;
&lt;li&gt;linear time construction  &lt;/li&gt;
&lt;li&gt;ongest repeated substring, longest common substring, longest palindromic substring, substring search, tandem repeats... 好有用!!...   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="summery_1"&gt;Summery&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week4_1/pasted_image011.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 3-2 Radix Sorts</title><link href="https://x-wei.github.io/notes/algoII_week3_2.html" rel="alternate"/><published>2015-11-23T00:00:00+01:00</published><updated>2015-11-23T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-23:/notes/algoII_week3_2.html</id><summary type="html">&lt;p&gt;This week: string sort.  &lt;/p&gt;
&lt;h1 id="1-strings-in-java"&gt;1. Strings in Java&lt;/h1&gt;
&lt;h3 id="char-data-type"&gt;char data type&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;char in C&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;8-bit integer, 256 characters, 7-bit ASCII code  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;char in Java&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;16-bit Unicode&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="string-data-type"&gt;String data type&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;String&lt;/code&gt;: &lt;em&gt;immutable&lt;/em&gt; sequence of characters&lt;br/&gt;
operations: lengthe, ith char, substring, concatenate  &lt;/p&gt;
&lt;p&gt;implementation: using a &lt;code&gt;char[]&lt;/code&gt;, maintain a &lt;code&gt;length&lt;/code&gt; and an &lt;code&gt;offset …&lt;/code&gt;&lt;/p&gt;</summary><content type="html">&lt;p&gt;This week: string sort.  &lt;/p&gt;
&lt;h1 id="1-strings-in-java"&gt;1. Strings in Java&lt;/h1&gt;
&lt;h3 id="char-data-type"&gt;char data type&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;char in C&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;8-bit integer, 256 characters, 7-bit ASCII code  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;char in Java&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;16-bit Unicode&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="string-data-type"&gt;String data type&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;String&lt;/code&gt;: &lt;em&gt;immutable&lt;/em&gt; sequence of characters&lt;br/&gt;
operations: lengthe, ith char, substring, concatenate  &lt;/p&gt;
&lt;p&gt;implementation: using a &lt;code&gt;char[]&lt;/code&gt;, maintain a &lt;code&gt;length&lt;/code&gt; and an &lt;code&gt;offset.&lt;/code&gt; ⇒ substring methode is O(1) time.&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image.png"/&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;h3 id="stringbuilder-data-type"&gt;StringBuilder data type&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;StringBuilder&lt;/code&gt;: &lt;em&gt;mutable&lt;/em&gt; data type.&lt;br/&gt;
implementation: using a resizing &lt;code&gt;char[]&lt;/code&gt; array (ArrayList). &lt;br/&gt;
⇒ contat in (amortized) constant time, &lt;em&gt;substring in linear time&lt;/em&gt;!&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;ex.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;reverse a string: linear using StringBuilder, quad using String.   &lt;/li&gt;
&lt;li&gt;form an array of suffixes: quad (time&amp;amp;space) using StringBuilder, linear (time&amp;amp;space) using String.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image003.png"/&gt;&lt;br/&gt;
&lt;strong&gt;Longest Common Prefix:&lt;/strong&gt;&lt;br/&gt;
runs in linear/subinear time ⇒ &lt;code&gt;compareTo()&lt;/code&gt; for strings takes (sub)linear time!  &lt;/p&gt;
&lt;h3 id="alphabet"&gt;Alphabet&lt;/h3&gt;
&lt;p&gt;alphabet different for different type of string (ex. binary numbers, DNA, ...)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image004.png"/&gt;&lt;br/&gt;
def. &lt;strong&gt;Radix&lt;/strong&gt; &lt;code&gt;R&lt;/code&gt; is number of digits  in alphabet.   &lt;/p&gt;
&lt;h1 id="2-key-indexed-counting_1"&gt;2. Key-Indexed Counting&lt;/h1&gt;
&lt;p&gt;review of &lt;em&gt;compare-based&lt;/em&gt; sorting algorithms:&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image005.png"/&gt;&lt;br/&gt;
lower-bound for compare-based algorithms: ~&lt;em&gt;NlgN&lt;/em&gt; (=Lg(N!))&lt;br/&gt;
⇒ goal: do better by avoiding using compares.   &lt;/p&gt;
&lt;h3 id="key-indexed-counting"&gt;Key-indexed counting&lt;/h3&gt;
&lt;p&gt;is an algorithm to sort &lt;em&gt;by character(ex. sort array of string by their 1st character).&lt;/em&gt; &lt;br/&gt;
Assumption: keys are integers between 0 and R-1 (&amp;lt;&amp;lt;N, small integer).&lt;br/&gt;
⇒ use keys as array index, to sort an &lt;em&gt;array of N integers between 0 and R-1&lt;/em&gt;.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;count freq of each key index (of size &lt;em&gt;R+1&lt;/em&gt;)  &lt;/li&gt;
&lt;li&gt;using count array, compute a &lt;em&gt;cumulated freq&lt;/em&gt; (cumsum of &lt;code&gt;count[]&lt;/code&gt;)  &lt;/li&gt;
&lt;li&gt;the &lt;code&gt;cumsum[]&lt;/code&gt; array stores the &lt;strong&gt;index range&lt;/strong&gt; of each key index:   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;index range of key-i in sorted array is &lt;code&gt;[cumsum[i], cumsum[i+1]]&lt;/code&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;then get the sorted array by going through the array and using cumsum[] array  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image007.png"/&gt;⇒ &lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;keyIndexCounting&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;entries&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;range&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;0,R-1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;0&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;ai&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;ai+1&lt;/span&gt;&lt;span class="o"&gt;]++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cumulated&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;freq&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ranges&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sorted&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;should&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;be&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;cumsum[i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;ai&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;cumsum[ai&lt;/span&gt;&lt;span class="o"&gt;]++&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ai&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="analysis"&gt;analysis&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;running time: &lt;strong&gt;linear&lt;/strong&gt; in time and in space.   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;stable&lt;/strong&gt; sorting: that's why we need the cumsum and aux array...  &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-lsd-radix-sort_1"&gt;3. LSD Radix Sort&lt;/h1&gt;
&lt;p&gt;LSD = least significant digit (for string sorting)&lt;br/&gt;
(assume strings all of same length)&lt;br/&gt;
idea:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;consider chars from right to left   &lt;/li&gt;
&lt;li&gt;sort using dth character as key (using key-indexed counting)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;important: the key-indexed counting should be stable.&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h3 id="analysis_1"&gt;analysis&lt;/h3&gt;
&lt;p&gt;time: W * N (W=length of string)  &lt;/p&gt;
&lt;p&gt;correctness:&lt;br/&gt;
&lt;strong&gt;prop&lt;/strong&gt;. LSD sorting works&lt;br/&gt;
pf. by induction on i&lt;br/&gt;
prove that: after pass i, strings are sorted by last i characters.   &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LSDsort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;W&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;W&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;fixed&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;width&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;256&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;ASCII&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;chars&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;W&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="c1"&gt;--){//W passes  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;indexed&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;counting&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;at&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;digit&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;s&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s.charAt[d&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;range&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;s&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s.charAt[d&lt;/span&gt;&lt;span class="o"&gt;]++&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;place&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;if keys are binary numbers → break into bit characters then apply LSD.   &lt;/li&gt;
&lt;li&gt;if not fixed length → some fix..  &lt;/li&gt;
&lt;li&gt;sort 1 million 32-bit integers? (Google/Obama interview) ⇒ LSD string sort~   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="4-msd-radix-sort_1"&gt;4. MSD Radix Sort&lt;/h1&gt;
&lt;p&gt;most-significant-digit first (from left to right)&lt;br/&gt;
Idea.  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;partition array into R pieces according to first character (the count[] array is the partition)  &lt;/li&gt;
&lt;li&gt;&lt;em&gt;recursively&lt;/em&gt; sort each subarrays  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;variable length: end-of-string are treated as before any char&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h3 id="implementation_1"&gt;implementation&lt;/h3&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;by&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dth&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;character&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;R+2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;taking&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;account&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;into&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;end&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;strings&lt;/span&gt;&lt;span class="err"&gt;!!&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt; a[i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;end&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;=-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;cumsum&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;count[a[i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="err"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i-lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;attention&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;filled&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;instead&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;recursively&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;subarray&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;subarrays&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ranges&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stored&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;r+1&lt;/span&gt;&lt;span class="o"&gt;]-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="analysis_2"&gt;analysis&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;can recycle &lt;code&gt;aux[]&lt;/code&gt;, but &lt;em&gt;not&lt;/em&gt; &lt;code&gt;count[]&lt;/code&gt;.   &lt;/li&gt;
&lt;li&gt;too slow for small subarrays (if len(subarray)&amp;lt;&amp;lt;R)  &lt;/li&gt;
&lt;li&gt;huge nb of subarrays because of recursion   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;improvement ⇒ cutoff to insertion sort...   &lt;/p&gt;
&lt;p&gt;characteristics of MSD sort: &lt;br/&gt;
examines &lt;strong&gt;just enough chars&lt;/strong&gt; to sort. &lt;br/&gt;
→ can be sublinear in N. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h3 id="msd-vs-quicksort"&gt;MSD vs. quicksort&lt;/h3&gt;
&lt;p&gt;disadvantages for MSD:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;random access of memory (cache inefficient)  &lt;/li&gt;
&lt;li&gt;too many instructions in inner loop   &lt;/li&gt;
&lt;li&gt;extra space for count[]  &lt;/li&gt;
&lt;li&gt;extra space for aux[]  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;disadvantages for qsort:  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;NlgN nb of string compares  &lt;/li&gt;
&lt;li&gt;has to rescan many chars for keys with &lt;em&gt;long prefix matches&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="5-3-way-radix-quicksort_1"&gt;5. 3-way Radix Quicksort&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;⇒ combine benefits of qsort and MSD.&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image015.png"/&gt;&lt;br/&gt;
idea: do &lt;strong&gt;3-way partition by the dth character&lt;/strong&gt;. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;less overhead than &lt;em&gt;R-way&lt;/em&gt; partitioning for MSD  &lt;/li&gt;
&lt;li&gt;do not re-examine chars equal to the partitioning char  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;h3 id="implementation_2"&gt;Implementation&lt;/h3&gt;
&lt;p&gt;modification of the 3-way qsort.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;pointers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nl"&gt;invariant&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo,lt)&amp;lt;pivot, a(gt,hi&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lt,i&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;char&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;charAt&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="c1"&gt;--);  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;way&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;means&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;end&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;string&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="analysis_3"&gt;analysis&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;wrt. qsort:&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;from NlgN &lt;strong&gt;string&lt;/strong&gt; compares to NlgN &lt;strong&gt;char&lt;/strong&gt; compares.  &lt;/li&gt;
&lt;li&gt;avoids re-comparing long common prefixes.  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;wrt. MSD:&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;short inner loop  &lt;/li&gt;
&lt;li&gt;cache friendly  &lt;/li&gt;
&lt;li&gt;in-place  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;h1 id="6-suffix-arrays_1"&gt;6. Suffix Arrays&lt;/h1&gt;
&lt;p&gt;(&lt;em&gt;some applications of suffix array)&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="keyword-in-context-search"&gt;keyword-in-context search&lt;/h3&gt;
&lt;p&gt;given N chars (N huge), &lt;em&gt;preprocess&lt;/em&gt; it to enable fast substring search. &lt;br/&gt;
⇒ suffix sort  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;generate suffix array (linear time &amp;amp; space )  &lt;/li&gt;
&lt;li&gt;sort on the suffix ⇒ brings repeated suffixes together  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;h3 id="longest-repeated-substring"&gt;longest repeated substring&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;brute force algorithm  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;try all i, j as starts of indices, then compute longest common prefix (LCP)&lt;br/&gt;
→ O(D*N2) where D is length of longest repeated substring.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;⇒ use suffix array   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;sorting suffix array will bring repeated substrings together&lt;br/&gt;
java code:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;defined&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lrs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;substring&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;construct&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Arrays&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;==&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;using&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;way&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;radix&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;one&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pass&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;longest&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;repeated&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;substring&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;bigest&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lrs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;""&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="n"&gt;lrs&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lrs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;suffix&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;substring&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lcp&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lrs&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;lrs worst-case input&lt;/strong&gt;: &lt;em&gt;lrs very long&lt;/em&gt; (say N/2). &lt;br/&gt;
⇒ &lt;em&gt;quadratic&lt;/em&gt; for lrs and for sorting. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_2/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;p&gt;→ &lt;em&gt;improvement of lrs for worst-case performance:&lt;/em&gt;&lt;br/&gt;
&lt;strong&gt;Manber-Myers algo&lt;/strong&gt;&lt;br/&gt;
sketch:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;phase 0: sort suffix[] on 1st char   &lt;/li&gt;
&lt;li&gt;phase i: given suffix[] is sorted based on first 2^(i-1) chars → create suffix[] sorted on first 2^i chars.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;each phase: double the nb of chars sorted on. &lt;br/&gt;
maintain an inverse[] array, to make comparisons constant time. &lt;br/&gt;
performance: NlgN  &lt;/p&gt;
&lt;h2 id="string-sorting-summery_1"&gt;String sorting summery&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;can have linear sort: use chars as array index  &lt;/li&gt;
&lt;li&gt;sublinear sort: not all date need to be examined  &lt;/li&gt;
&lt;li&gt;3-way radix qsort is &lt;em&gt;asymptotically optimal&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 3-1 Maximum Flow</title><link href="https://x-wei.github.io/notes/algoII_week3_1.html" rel="alternate"/><published>2015-11-17T00:00:00+01:00</published><updated>2015-11-17T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-17:/notes/algoII_week3_1.html</id><summary type="html">&lt;h1 id="1-introduction-to-maxflow"&gt;1. Introduction to Maxflow&lt;/h1&gt;
&lt;h3 id="min-cut-pb"&gt;Min-cut pb&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;input: edge-weighted digraph G, each edge &lt;code&gt;e&lt;/code&gt; has weight(&lt;em&gt;"capacity"&lt;/em&gt;) &lt;code&gt;c[e]&lt;/code&gt;&amp;gt;=0, a &lt;em&gt;source vertex&lt;/em&gt; &lt;code&gt;s&lt;/code&gt;, a &lt;em&gt;target vertex&lt;/em&gt; &lt;code&gt;t&lt;/code&gt;.    &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;def&lt;/strong&gt;. an &lt;strong&gt;st-cut &lt;/strong&gt;&lt;code&gt;(A,B)&lt;/code&gt; is a partition of vertices into 2 disjoint sets A and B, with &lt;code&gt;s&lt;/code&gt; in set &lt;code&gt;A&lt;/code&gt; and …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;h1 id="1-introduction-to-maxflow"&gt;1. Introduction to Maxflow&lt;/h1&gt;
&lt;h3 id="min-cut-pb"&gt;Min-cut pb&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;input: edge-weighted digraph G, each edge &lt;code&gt;e&lt;/code&gt; has weight(&lt;em&gt;"capacity"&lt;/em&gt;) &lt;code&gt;c[e]&lt;/code&gt;&amp;gt;=0, a &lt;em&gt;source vertex&lt;/em&gt; &lt;code&gt;s&lt;/code&gt;, a &lt;em&gt;target vertex&lt;/em&gt; &lt;code&gt;t&lt;/code&gt;.    &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;def&lt;/strong&gt;. an &lt;strong&gt;st-cut &lt;/strong&gt;&lt;code&gt;(A,B)&lt;/code&gt; is a partition of vertices into 2 disjoint sets A and B, with &lt;code&gt;s&lt;/code&gt; in set &lt;code&gt;A&lt;/code&gt; and &lt;code&gt;t&lt;/code&gt; in set &lt;code&gt;B&lt;/code&gt;.    &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;def&lt;/strong&gt;. the &lt;strong&gt;capacity&lt;/strong&gt; of a cut &lt;code&gt;(A,B)&lt;/code&gt; is sum of capacities of edges going &lt;em&gt;from A to B&lt;/em&gt; &lt;em&gt;(not considering B to A)&lt;/em&gt;.    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image.png"/&gt; &lt;br/&gt;
⇒ min-cut pb: find the cut &lt;strong&gt;(A,B)&lt;/strong&gt; with min-capacity.    &lt;/p&gt;
&lt;h3 id="max-flow-pb"&gt;Max-flow pb&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;same input: graph G, source s, target t   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;def.&lt;/strong&gt; an &lt;strong&gt;st-flow&lt;/strong&gt; is an assignment of values to edges &lt;code&gt;f: e→f[e]&lt;/code&gt; such that:    &lt;ul&gt;
&lt;li&gt;capacity constraint: &lt;code&gt;0&amp;lt;=f[e]&amp;lt;=c[e]&lt;/code&gt; for any e;   &lt;/li&gt;
&lt;li&gt;local equilibrium: for any vertex v (other than s or t), &lt;em&gt;inflow=outflow&lt;/em&gt;;   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;def.&lt;/strong&gt; the &lt;strong&gt;value&lt;/strong&gt; of a flow &lt;code&gt;f&lt;/code&gt; is the inflow at &lt;code&gt;t&lt;/code&gt;. (assume no ingoing edge to s or outgoing edge to t)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image001.png"/&gt; &lt;br/&gt;
⇒ max-flow pb: find &lt;code&gt;f&lt;/code&gt; with max value.    &lt;/p&gt;
&lt;p&gt;remark: max-flow and min-cut are dual problems.    &lt;/p&gt;
&lt;h1 id="2-ford-fulkerson-algorithm_1"&gt;2. Ford-Fulkerson Algorithm&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;def.&lt;/strong&gt; given a flow &lt;code&gt;f&lt;/code&gt; for a graph, an &lt;strong&gt;"augment path"&lt;/strong&gt; is an &lt;strong&gt;undirected&lt;/strong&gt; path form &lt;code&gt;s&lt;/code&gt; to &lt;code&gt;t&lt;/code&gt;, if there exist &lt;code&gt;df&amp;gt;0&lt;/code&gt; (&lt;em&gt;"bottleneck capacity"&lt;/em&gt;) such that:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;for forward edges e: can augment flow by &lt;code&gt;df&lt;/code&gt; (not full: &lt;code&gt;f[e]+df&amp;lt;=c[e]&lt;/code&gt;)   &lt;/li&gt;
&lt;li&gt;for backward edges: can decrease flow by &lt;code&gt;df&lt;/code&gt; (not empty: &lt;code&gt;f[e]-df&amp;gt;=0&lt;/code&gt;)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;def. &lt;strong&gt;residual capacity&lt;/strong&gt; &lt;ul&gt;
&lt;li&gt;for forward edge e, &lt;em&gt;residual-cap = c[e]-f[e]&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;for backward edge e, &lt;em&gt;residual-cap = f[e]&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ an aug-path is a path where &lt;em&gt;each edge has residual capacity &amp;gt;0&lt;/em&gt;.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;blocking edges&lt;/strong&gt;: &lt;em&gt;full forward edge&lt;/em&gt; or &lt;em&gt;empty backward edge.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;→ idea: increase flow along augment paths. &lt;br/&gt;
&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;start: 0 flow: &lt;code&gt;f[e]=0&lt;/code&gt; for all e.    &lt;/li&gt;
&lt;li&gt;find an augment path (and the corresponding &lt;code&gt;df&lt;/code&gt;) in graph, and change the flows along the path by &lt;code&gt;+/-df&lt;/code&gt;.   &lt;/li&gt;
&lt;li&gt;loop until no augment path exists. (ie. all path s→t are blocked either by a &lt;em&gt;full forward edge&lt;/em&gt; or an &lt;em&gt;empty backward edge, &lt;/em&gt;ie. by an edge with 0 residual capacity)   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;FF is a gernel algorithm:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-maxflow-mincut-theorem"&gt;3. Maxflow-Mincut Theorem&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;def&lt;/strong&gt;. for a cut (A,B), the &lt;strong&gt;net flow&lt;/strong&gt; across the cut (&lt;em&gt;netflow(A,B)&lt;/em&gt;) is the sum of flows from A to B minus flows from B to A.    &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;[flow-value Lemma]&lt;/strong&gt; &lt;br/&gt;
For any flow &lt;code&gt;f&lt;/code&gt; and any cut &lt;code&gt;(A,B)&lt;/code&gt;⇒  &lt;em&gt;netflow(A,B) = value(f).&lt;/em&gt; &lt;br/&gt;
&lt;em&gt;pf.&lt;/em&gt; &lt;br/&gt;
induction on the size of set B. &lt;br/&gt;
&lt;em&gt; base case, when B={t}, by def we have &lt;/em&gt;netflow(A,B) = value(f)&lt;em&gt; &lt;br/&gt;
&lt;/em&gt; when moving any vertex v from A to B: &lt;br/&gt;
    * netflow(A, B) augment by &lt;em&gt;flow(A→v)+flow(B→v)=inflow(v)&lt;/em&gt;,  &lt;br/&gt;
    * netflow(A, B) decrease by &lt;em&gt;flow(v→A)+flow(v→B)=outflow(v)&lt;/em&gt;,  &lt;br/&gt;
    * by equilibrium of flow, &lt;em&gt;netflow(A',B')=netflow(A,B)=value(f)&lt;/em&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;ex. (A: gray vertices, B: white vertices) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;[cor] &lt;em&gt;outflow(s)=inflow(t)=value(f)&lt;/em&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;[weak duality]&lt;/strong&gt; &lt;br/&gt;
For &lt;em&gt;any&lt;/em&gt; flow &lt;code&gt;f&lt;/code&gt; and &lt;em&gt;any&lt;/em&gt; cut &lt;code&gt;(A,B)&lt;/code&gt;, ⇒ &lt;em&gt;value(f) &amp;lt;= capacity(A,B).&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[Augmenting path Th]&lt;/strong&gt; &lt;br/&gt;
A flow &lt;code&gt;f&lt;/code&gt; is maxflow &lt;em&gt;iff&lt;/em&gt; there is no augment path.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[maxflow-mincut Th]&lt;/strong&gt; &lt;br/&gt;
&lt;strong&gt;value(maxflow) = capacity(mincut).&lt;/strong&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;em&gt;pf.&lt;/em&gt; &lt;br/&gt;
for any flow &lt;code&gt;f&lt;/code&gt;, prove the equivalence of the 3 following statements: &lt;br/&gt;
i. there exists a cut st: &lt;em&gt;capacity(cut) = value(f).&lt;/em&gt; &lt;br/&gt;
ii. &lt;code&gt;f&lt;/code&gt; is a maxflow. &lt;br/&gt;
iii. there is no augmenting path wrt &lt;code&gt;f&lt;/code&gt;.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;[i⇒ii]   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;suppose cut(A,B) st: &lt;em&gt;capacity(A,B)=value(f)&lt;/em&gt; &lt;br/&gt;
⇒ by weak duality, for any other flow f', &lt;em&gt;vlaue(f')&amp;lt;=capacity(A,B)=value(f)&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;[ii⇒iii] (eqv to prove ~iii⇒~ii)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;suppose there is an aug-path from s to t, of bottleneck capacity=df, &lt;br/&gt;
⇒ by improving f with df, we get a f' &amp;gt; f   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;[iii⇒i]   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;suppose there is no aug-path, ie, &lt;em&gt;all path from s to t are blocked by some full-forward edge or empty backward edge.&lt;/em&gt; &lt;br/&gt;
⇒ let A:=vertices connected with s by a path with no blocking edges, and B := the rest &lt;br/&gt;
(&lt;em&gt;so&lt;/em&gt; &lt;em&gt;once we get a maxflow, we can &lt;/em&gt;&lt;strong&gt;compute the mincut&lt;/strong&gt;&lt;em&gt; in this way&lt;/em&gt;) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image006.png"/&gt; &lt;br/&gt;
→ for all edges across A and B, all forward edges are full, all backward edges are empty &lt;br/&gt;
⇒ capacity(A,B) = netflow(A,B) = value(f) by flow-value lemma &lt;br/&gt;
CQFD... 过瘾...   &lt;/p&gt;
&lt;h1 id="4-running-time-analysis"&gt;4. Running Time Analysis&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;getting a mincut form maxflow? → easy (as discussed in the pf above)   &lt;/li&gt;
&lt;li&gt;computing an aug-path? → &lt;strong&gt;BFS&lt;/strong&gt; &lt;/li&gt;
&lt;li&gt;does FF algo always terminate? how many augmentations? → ...   &lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="integer-capacity-graphs"&gt;integer capacity graphs&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;special case of FF algo&lt;/em&gt;: edge capacities are &lt;em&gt;integers&lt;/em&gt; between 1 and U.    &lt;/p&gt;
&lt;p&gt;invariant: flow is always integer all along FF algo.   &lt;/p&gt;
&lt;p&gt;[prop] nb of augmentations &amp;lt;= value of maxflow. &lt;br/&gt;
pf. each augmentation will add flow by &amp;gt;=1.    &lt;/p&gt;
&lt;p&gt;[integrality Th] There exist an integer-valued maxflow.    &lt;/p&gt;
&lt;h3 id="bad-case-for-ff"&gt;Bad case for FF&lt;/h3&gt;
&lt;p&gt;nb of augmentation == value of maxflow &lt;br/&gt;
(each time, the path through the middle edge is chosen as aug-path) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image008.png"/&gt; &lt;br/&gt;
&lt;strong&gt;can be easily avoided&lt;/strong&gt;⇒  by using shortest(nb of edges)/fastest(biggest df) path  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;p&gt;Performance of FF depends on the algo for choosing aug-path: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;h1 id="5-java-implementation_1"&gt;5. Java Implementation&lt;/h1&gt;
&lt;h3 id="representation-of-flow-graph"&gt;representation of flow graph&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;flow edge:   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;each e= v→w, have flow f[e] and capacity c[e].   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;flow graph:   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;put e in both v and w's adj-list.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;flow augmentation (by delta)   &lt;ul&gt;
&lt;li&gt;for forward edge e, f[e] += delta   &lt;/li&gt;
&lt;li&gt;for backward edge e, f[e] -= delta   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="residual-graph-gr"&gt;Residual graph Gr&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;def&lt;/strong&gt;. For a flow &lt;code&gt;f&lt;/code&gt; and a graph &lt;code&gt;G&lt;/code&gt;,  the &lt;strong&gt;residual graph&lt;/strong&gt; &lt;code&gt;Gr&lt;/code&gt; is obtained by:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;for each edge &lt;code&gt;e=v→w&lt;/code&gt;, (with &lt;code&gt;c[e]&lt;/code&gt; and &lt;code&gt;f[e]&lt;/code&gt;) in &lt;code&gt;G&lt;/code&gt;, put in &lt;code&gt;Gr&lt;/code&gt;: &lt;br/&gt;
&lt;em&gt; &lt;code&gt;e1=v→w&lt;/code&gt;, with weight=&lt;code&gt;c[e]-f[e]&lt;/code&gt; &lt;br/&gt;
&lt;/em&gt; &lt;code&gt;e2=w→v&lt;/code&gt;, with weight=&lt;code&gt;f[e]&lt;/code&gt; (即两个方向上的weight都为residual capacity)   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;(rmq: &lt;code&gt;Gr&lt;/code&gt; is just a weighted digraph, not a flow graph)   &lt;/p&gt;
&lt;p&gt;[prop] &lt;strong&gt;Augment path in &lt;/strong&gt;&lt;code&gt;G&lt;/code&gt;&lt;strong&gt; is equivalent to a path in &lt;/strong&gt;&lt;code&gt;Gr&lt;/code&gt; (&lt;code&gt;df&lt;/code&gt; of aug-path in &lt;code&gt;G&lt;/code&gt; = min edge weight in &lt;code&gt;Gr&lt;/code&gt;)&lt;strong&gt;.&lt;/strong&gt; &lt;br/&gt;
(但是实现的时候其实不用显式构造Gr, 只需BFS的时候修改一下即可) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h3 id="apis"&gt;APIs&lt;/h3&gt;
&lt;p&gt;这里的API设计的非常合理... 导致每一部分的代码量都不大... NB   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;flow-edge:  &lt;br/&gt;
rmq. both calculate residual-cap and augmentation need to specify a &lt;em&gt;direction&lt;/em&gt;, so we need a index v as parameter for these 2 functions.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class FlowEdge{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    private final int v, w;   &lt;/span&gt;
&lt;span class="code-line"&gt;    private final double capacity;   &lt;/span&gt;
&lt;span class="code-line"&gt;    private double flow=0.0;   &lt;/span&gt;
&lt;span class="code-line"&gt;    FlowEdge(int v, int w, double cap);   &lt;/span&gt;
&lt;span class="code-line"&gt;    int from();   &lt;/span&gt;
&lt;span class="code-line"&gt;    int to();   &lt;/span&gt;
&lt;span class="code-line"&gt;    int other(int v);   &lt;/span&gt;
&lt;span class="code-line"&gt;    double capacity();   &lt;/span&gt;
&lt;span class="code-line"&gt;    double flow();   &lt;/span&gt;
&lt;span class="code-line"&gt;    double residualCapTo(int v);// residual capacity   &lt;/span&gt;
&lt;span class="code-line"&gt;    void addFlowTo(int v, double delta);// augment residual flow   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;flow graph:  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;FlowNetwork&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;FlowEdge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;adj&lt;/span&gt;&lt;span class="c1"&gt;;//use adj-list representation for flow graph   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;FlowNetwork&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;V&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;addEdge&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;FlowEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;e&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;FlowEdge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;adj&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;// both incoming and outgoing edges   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;...&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;FF algo:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;use a function &lt;code&gt;hasAugPath()&lt;/code&gt; to test termination   &lt;/li&gt;
&lt;li&gt;use a function &lt;code&gt;bottleNeck()&lt;/code&gt; to get delta   &lt;/li&gt;
&lt;li&gt;if a augpath is found, use two arrays &lt;code&gt;reached[]&lt;/code&gt; and &lt;code&gt;edgeTo[]&lt;/code&gt; to get the augpath (find the path &lt;em&gt;backwards&lt;/em&gt;).    &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;code:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;FordFulkerson&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;indicates&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="c1"&gt;--&amp;gt;v exists in Gr, used in DFS   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;FlowEdge&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;on&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="c1"&gt;--&amp;gt;v   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;0.0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;flow&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;FordFulkerson&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;FlowNetwork&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hasAugPath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delta&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;bottleNeck&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;addFlowTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delta&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delta&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;time&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;flow&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;augments&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;by&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delta&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bottleNeck&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;bottleneck&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;cap&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;residual&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;flow&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;on&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aut&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bottleneck&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;9999999&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;assert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aug&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;should&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;exsit&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;bottleneck&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;bottleneck&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bottleneck&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hasAugPath&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;FlowNetwork&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;perform&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;BFS&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LinkedList&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;FlowEdge&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;deque&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;FlowEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;residualCapTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;modified&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;BFS&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;valid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;those&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;with&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="n"&gt;residualCap&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;reached&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;by&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;BFS&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;enqueue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;BFS&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;loop&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;false&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;FF&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="6-maxflow-applications_1"&gt;6. Maxflow Applications&lt;/h1&gt;
&lt;p&gt;关键是建模很巧妙... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;h3 id="ex1-bipartite-matching-pb"&gt;ex1. bipartite matching pb&lt;/h3&gt;
&lt;p&gt;二分图的最大匹配问题. (有点像marriage stable问题...但是不一样 因为没有preference order) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image013.png"/&gt; &lt;br/&gt;
⇒ is there a way to match all students to a job? &lt;br/&gt;
ie. &lt;em&gt;given a bipartite graph, find a perfect matching.&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image014.png"/&gt; &lt;br/&gt;
&lt;strong&gt;modeling&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;add source &lt;code&gt;s&lt;/code&gt; and target &lt;code&gt;t&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;all edges from &lt;code&gt;s&lt;/code&gt; to students: capacity=1   &lt;/li&gt;
&lt;li&gt;all edges from companies to &lt;code&gt;t&lt;/code&gt;: capacity=1   &lt;/li&gt;
&lt;li&gt;all edges from student to company: capacity=INF   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;⇒ find maxflow in the graph &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image015.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;when no perfect matching: mincut can explain why&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image016.png"/&gt; &lt;br/&gt;
in the above case, student 2,4,5 can only be matched to 7,10 &lt;br/&gt;
⇒ mincut can help us find such cases!   &lt;/p&gt;
&lt;p&gt;&lt;em&gt;recall: how to get mincut from maxflow&lt;/em&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;mincut = (A,B), where: &lt;br/&gt;
A:=vertices connected with s by a path with non blocking edges,  &lt;br/&gt;
B := the rest &lt;br/&gt;
(&lt;em&gt;blocking edges: full forward edge or empty backward edge on path&lt;/em&gt;)   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;ex. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;let S=students on s side of mincut (in above case, &lt;em&gt;S={2,4,5}&lt;/em&gt;)   &lt;/li&gt;
&lt;li&gt;let T=companies on s side of mincut (in above case, T&lt;em&gt;={7,10}&lt;/em&gt;)   &lt;/li&gt;
&lt;li&gt;|S|&amp;gt;|T|, that's why no perfect matching!   &lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="ex2-baseball-elimination"&gt;ex2. baseball elimination&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image018.png"/&gt; &lt;br/&gt;
(前三列是目前成绩, 后面四列是接下来赛程矩阵) &lt;br/&gt;
Montreal is mathematically eliminated → easy to see &lt;br/&gt;
→ Philly is mathematically eliminated also !   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;another case:   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image019.png"/&gt; &lt;br/&gt;
Detroit is mathematically eliminated ! &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image020.png"/&gt; &lt;br/&gt;
whether team-4 still has a chance to win? &lt;br/&gt;
&lt;strong&gt;modelling&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;remaining games flow from s to t.    &lt;/li&gt;
&lt;li&gt;use team-pairs ans teams as vertices   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;carefully chosen capacities&lt;/em&gt;(see below)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week3_1/pasted_image021.png"/&gt; &lt;br/&gt;
⇒ team 4 could win iff all flow from s are full (ie. all match points can be repartitioned over other teams &lt;em&gt;without depassing team 4's maximum wins&lt;/em&gt;). &lt;br/&gt;
总之很巧妙....   &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 2-2 Shortest Paths</title><link href="https://x-wei.github.io/notes/algoII_week2_2.html" rel="alternate"/><published>2015-11-15T00:00:00+01:00</published><updated>2015-11-15T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-15:/notes/algoII_week2_2.html</id><summary type="html">&lt;h1 id="1-shortest-paths-apis"&gt;1. Shortest Paths APIs&lt;/h1&gt;
&lt;p&gt;context: &lt;em&gt;directe, weighted graphs&lt;/em&gt;.     &lt;/p&gt;
&lt;h3 id="shortest-path-variants"&gt;shortest path variants&lt;/h3&gt;
&lt;p&gt;in terms of vertices:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;source-sink: form one vertex to another   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;single source&lt;/strong&gt;: from one vertex to all others (considered in this lecture)   &lt;/li&gt;
&lt;li&gt;all pairs   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;constraints on edge weights:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;nonnegative weights    &lt;/li&gt;
&lt;li&gt;arbitary weights   &lt;/li&gt;
&lt;li&gt;eculidean    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;cycles:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;no directed cycles   &lt;/li&gt;
&lt;li&gt;no negative …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;h1 id="1-shortest-paths-apis"&gt;1. Shortest Paths APIs&lt;/h1&gt;
&lt;p&gt;context: &lt;em&gt;directe, weighted graphs&lt;/em&gt;.     &lt;/p&gt;
&lt;h3 id="shortest-path-variants"&gt;shortest path variants&lt;/h3&gt;
&lt;p&gt;in terms of vertices:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;source-sink: form one vertex to another   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;single source&lt;/strong&gt;: from one vertex to all others (considered in this lecture)   &lt;/li&gt;
&lt;li&gt;all pairs   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;constraints on edge weights:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;nonnegative weights    &lt;/li&gt;
&lt;li&gt;arbitary weights   &lt;/li&gt;
&lt;li&gt;eculidean    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;cycles:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;no directed cycles   &lt;/li&gt;
&lt;li&gt;no negative cycles   &lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="apis"&gt;APIs&lt;/h3&gt;
&lt;p&gt;for weighted directed edge:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class DirectedEdge{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    DirectedEdge(int v, int w, double weight);   &lt;/span&gt;
&lt;span class="code-line"&gt;    int from();   &lt;/span&gt;
&lt;span class="code-line"&gt;    int to();   &lt;/span&gt;
&lt;span class="code-line"&gt;    double weight();   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;for edge-weighted digraph:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class EdgeWeightedDigraph{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    private final Bag&amp;lt;DirectedEdge&amp;gt;[] adj;    &lt;/span&gt;
&lt;span class="code-line"&gt;    EdgeWeightedDigraph(int V);   &lt;/span&gt;
&lt;span class="code-line"&gt;    void addEdge(DirectedEdge e);   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;DirectedEdge&amp;gt; adj(int v);   &lt;/span&gt;
&lt;span class="code-line"&gt;    int V();   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;for single source shortest-path:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class SP{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    SP(EdgeWeightedDigraph G, int s);//s is the source node   &lt;/span&gt;
&lt;span class="code-line"&gt;    double distTo(int v);//dist from s to v   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;DirectedEdge&amp;gt; pathTo(int v);// shortest path from s to v   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="2-shortest-path-properties_1"&gt;2. Shortest path properties&lt;/h1&gt;
&lt;p&gt;goal: single-source shortest path &lt;br/&gt;
&lt;strong&gt;prop&lt;/strong&gt;. a &lt;strong&gt;shortest-path-tree&lt;/strong&gt; (SPT) exists.  &lt;br/&gt;
这个结论以前没见过... 不太evident吧... 没有太想明白 &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image.png"/&gt; &lt;br/&gt;
⇒ consequence: can represent this SPT by 2 vertex-indexted arrays:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;double distTo[v]&lt;/code&gt; = shortest path length s → v   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;DirectedEdge edgeTo[v]&lt;/code&gt; = last edge to v in shortest path, &lt;code&gt;edgeTo[s] = null&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pathTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;e.from&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;path&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="edge-relaxation"&gt;Edge relaxation&lt;/h3&gt;
&lt;p&gt;dynamic prog:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;distTo[v] = length of &lt;strong&gt;known&lt;/strong&gt; shortest path from s to v   &lt;/li&gt;
&lt;li&gt;distTo[w] = length of &lt;strong&gt;known&lt;/strong&gt; shortest path from s to w   &lt;/li&gt;
&lt;li&gt;edgeTo[w] = last edge in the &lt;strong&gt;known&lt;/strong&gt; shortest path form s to w   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(consider edges one by one) &lt;br/&gt;
&lt;strong&gt;def&lt;/strong&gt;. edge e = v--&amp;gt;w &lt;strong&gt;relaxes&lt;/strong&gt; if e.weight+distTo[v] &amp;lt; distTo[w]. → update distTo[w] and edgeTo[w]. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;&lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;distTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="optimality-conditions"&gt;optimality conditions&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. optimality conditions &lt;br/&gt;
distTo[] is the solution &lt;em&gt;iff&lt;/em&gt;:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;distTo[s] = 0   &lt;/li&gt;
&lt;li&gt;distTo[v] is the weight of some path from  s to v   &lt;/li&gt;
&lt;li&gt;for any edge e = v → w, distTo[w] &amp;lt;= distTo[v]+e.weight()   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;h3 id="generic-algo"&gt;Generic algo&lt;/h3&gt;
&lt;p&gt;just relax all edges... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image004.png"/&gt; &lt;br/&gt;
&lt;strong&gt;prop&lt;/strong&gt;. the above generic algo gives the SPT from s.    &lt;/p&gt;
&lt;p&gt;implementations of the algo:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Dijkstra (nonnegative edge)   &lt;/li&gt;
&lt;li&gt;Topological sort (!) (no directed cycles)   &lt;/li&gt;
&lt;li&gt;Bellman-Ford (no negative directed cycles)   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-dijkstras-algorithm_1"&gt;3. Dijkstra's Algorithm&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;(non-negative edges)&lt;/em&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;consider vertices in increasing distance from s.*    &lt;/li&gt;
&lt;li&gt;add vertex to the SPT, relax all edges from that vertex.    &lt;/li&gt;
&lt;li&gt;each time: take the closest vertex to s that is not in the SPT (ie. whose dist is not determined yet), add the vertex, and relax all its outgoing edges.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. Dijkstra works. &lt;br/&gt;
pf.  &lt;br/&gt;
&lt;em&gt; each edge e = v → w is considered exactly once (when vertex v is added to SPT). distTo[w] &amp;lt;= distTo[v]+e.weight() after relaxing e &lt;br/&gt;
&lt;/em&gt; ineq holds until algo terminates &lt;br/&gt;
    * distTo[w] decrease monotonely, &lt;br/&gt;
    * distTo[v] will not change because each time we choose distTo[v] smallest, and all edges non-negative.  &lt;br/&gt;
* CQFD by optimality condition.   &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;Use an &lt;code&gt;IndexMinPQ&lt;/code&gt; to store vertices.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DijkstraSP&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;IndexMinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="k"&gt;Double&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;DijkstraSP&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;EdgeWeightedDigraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;IndexMinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="k"&gt;Double&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;999999&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;           &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delMin&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;decrease&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;or&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;edgeTo&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;decreaseKey&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Dijkstra is in fact a Prim algorithm ! &lt;/strong&gt;&lt;em&gt;Both are algos that compute a spanning tree.&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;in Prim: each time takes the vertex &lt;em&gt;closest to the tree &lt;/em&gt;(and is for undirected graph).   &lt;/li&gt;
&lt;li&gt;in Dijkstra: each time takes the vertex &lt;em&gt;closest to source s &lt;/em&gt;(and is for directed graph).   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image005.png"/&gt; &lt;br/&gt;
DFS BFS are also computing spanning tree!  &lt;br/&gt;
...NB!!   &lt;/p&gt;
&lt;h3 id="complexity"&gt;complexity&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;V insertions to PQ (each vertex is added to the SPT)   &lt;/li&gt;
&lt;li&gt;V delMin from PQ    &lt;/li&gt;
&lt;li&gt;E decrease key   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ depends on the PQ implementation.  &lt;br/&gt;
in our implementation, &lt;strong&gt;O(ElogV)&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-edge-weighted-dags_1"&gt;4. Edge-Weighted DAGs&lt;/h1&gt;
&lt;p&gt;in a DAG, it's easier to find the shortest path ? &lt;br/&gt;
⇒ yes!  &lt;br/&gt;
simple algo:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;consider vertices in topological order   &lt;/li&gt;
&lt;li&gt;relax outgoing edges form this vertex.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;h3 id="correctness"&gt;correctness&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;.   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;topo-sort algo computes SPT in any DAG (&lt;em&gt;even with negative weights&lt;/em&gt;) in time &lt;strong&gt;O(E+V) &lt;/strong&gt;&lt;em&gt;(linear time!)&lt;/em&gt;.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;em&gt;pf.&lt;/em&gt; &lt;br/&gt;
&lt;em&gt; each edge is relaxed exactely once. distTo[w] &amp;lt;= distTo[v]+e.weight() after relaxing e &lt;br/&gt;
&lt;/em&gt; ineq holds until the algo terminates because:  &lt;br/&gt;
    * distTo[w] decrease monotonely, &lt;br/&gt;
    * distTo[v] will not change because of topo-order, no edge pointing to v after v is relaxed.  &lt;br/&gt;
* CQFD   &lt;/p&gt;
&lt;h3 id="implementation_1"&gt;implementation&lt;/h3&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;AsyclicSP&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;AsyclicSP(EdgeWeightedDigraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;G,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;s){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;init&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;dist&lt;/span&gt;&lt;span class="cp"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;edgeTo&lt;/span&gt;&lt;span class="cp"&gt;[]&lt;/span&gt;&lt;span class="err"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;Topological&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;topo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;Topological(G)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;for(int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;topo&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;order&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nf"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="application"&gt;application&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;seam-carving&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Resizing images &lt;em&gt;non-uniformly&lt;/em&gt; without distortion.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image008.png"/&gt; &lt;br/&gt;
好神奇! &lt;br/&gt;
Grid DAG of pixels, edges are pointed to 3 downward neighbors. &lt;br/&gt;
横向缩小: 删掉一个"seam" &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;longest path in DAG → &lt;em&gt;just negate all edge weights&lt;/em&gt;, as this algo is OK for negative edges.    &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;parallel job scheduling &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image010.png"/&gt; &lt;br/&gt;
感觉有点运筹的意思, 关键是建立一个DAG, 比较有技巧性:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;add source and sink    &lt;/li&gt;
&lt;li&gt;split each job to 2 vertices (begin and end)   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image011.png"/&gt; &lt;br/&gt;
⇒ use longest path to schedule jobs   &lt;/p&gt;
&lt;h1 id="5-negative-weights_1"&gt;5. Negative Weights&lt;/h1&gt;
&lt;p&gt;只是给所有边增加weight并&lt;strong&gt;不能&lt;/strong&gt;解决负权边问题.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image013.png"/&gt; &lt;br/&gt;
⇒ need a different algo.   &lt;/p&gt;
&lt;p&gt;prop. SPT exists &lt;em&gt;iff&lt;/em&gt; there is no &lt;em&gt;negative cycles.&lt;/em&gt; &lt;/p&gt;
&lt;h3 id="bellman-ford"&gt;Bellman-Ford&lt;/h3&gt;
&lt;p&gt;一句话总结Bellman算法: 每次relax所有的边, 进行V次. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image014.png"/&gt; &lt;br/&gt;
(&lt;em&gt;因为relax k次以后, s到v的最短路径的长度小于等于k.&lt;/em&gt;)   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. Bellman-Ford works, complexity is &lt;strong&gt;O(EV)&lt;/strong&gt;.  &lt;br/&gt;
pf.  &lt;br/&gt;
after i passes, found shortest path contain at most i edges.    &lt;/p&gt;
&lt;p&gt;code:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;BellmanFordSP&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;BellmanFordSP(EdgeWeightedDigraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;G,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;s){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;init&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;dist&lt;/span&gt;&lt;span class="cp"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;edgeTo&lt;/span&gt;&lt;span class="cp"&gt;[]&lt;/span&gt;&lt;span class="err"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;for(int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;i=0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;i&amp;lt;G.V()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;i++)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;for(DirectedEdge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nf"&gt;relax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="improvement"&gt;improvement&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;if dist[v] is not changed during one pasee → no need to relax incoming edges any more.&lt;/em&gt; &lt;br/&gt;
    → much faster in practice.    &lt;/p&gt;
&lt;p&gt;FIFO implementation: maintain a queue of vertices whoses dist is changed.    &lt;/p&gt;
&lt;h3 id="finding-negative-cycle"&gt;Finding negative cycle&lt;/h3&gt;
&lt;p&gt;add two method to SP:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;boolean hasNegCycle();   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;Iterable&amp;lt;DirectedEdge&amp;gt; negCycle();&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;.   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;if a vertex u is updated in phase V, there exists a negative cycle, and can track edgeTo[u] to find the cycle.    &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;原因是最短路径的长度小于V, 如果大于V则说明存在negative cycle.  &lt;/p&gt;
&lt;h3 id="negative-cycle-application"&gt;negative cycle application&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;arbitrage detection&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image018.png"/&gt; &lt;br/&gt;
建模: 
graph of currencies, edge weight = exchange weight (complete graph). &lt;br/&gt;
    ⇒ &lt;em&gt;find a cycle whose product of edge is &amp;gt;1.&lt;/em&gt; &lt;br/&gt;
        ⇒ &lt;strong&gt;take logs&lt;/strong&gt; to make a shortest-path pb. &lt;br/&gt;
            ⇒ take minus log, then try to find a negative cycle.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image020.png"/&gt; &lt;br/&gt;
NB!!   &lt;/p&gt;
&lt;h1 id="summery_1"&gt;Summery&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image015.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_2/pasted_image021.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 2-1 Minimum Spanning Trees</title><link href="https://x-wei.github.io/notes/algoII_week2_1.html" rel="alternate"/><published>2015-11-11T00:00:00+01:00</published><updated>2015-11-11T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-11:/notes/algoII_week2_1.html</id><summary type="html">&lt;h1 id="1-introduction-to-msts"&gt;1. Introduction to MSTs&lt;/h1&gt;
&lt;p&gt;Given: undirected connecte graph &lt;code&gt;G&lt;/code&gt; with positive edge weights.  &lt;br/&gt;
def. &lt;strong&gt;Spanning tree &lt;/strong&gt;&lt;code&gt;T&lt;/code&gt; &lt;br/&gt;
is a subgraph of &lt;code&gt;G&lt;/code&gt;, that is both tree (&lt;em&gt;connected, acyclic&lt;/em&gt;) and spanning(&lt;em&gt;all vertices are included&lt;/em&gt;).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image-0.png"/&gt; &lt;br/&gt;
⇒ Goal: find a spanning tree with minimum weight sum.   &lt;/p&gt;
&lt;h1 id="2-greedy-algorithm"&gt;2. Greedy Algorithm&lt;/h1&gt;
&lt;p&gt;assumptions for simplification:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;edge …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;h1 id="1-introduction-to-msts"&gt;1. Introduction to MSTs&lt;/h1&gt;
&lt;p&gt;Given: undirected connecte graph &lt;code&gt;G&lt;/code&gt; with positive edge weights.  &lt;br/&gt;
def. &lt;strong&gt;Spanning tree &lt;/strong&gt;&lt;code&gt;T&lt;/code&gt; &lt;br/&gt;
is a subgraph of &lt;code&gt;G&lt;/code&gt;, that is both tree (&lt;em&gt;connected, acyclic&lt;/em&gt;) and spanning(&lt;em&gt;all vertices are included&lt;/em&gt;).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image-0.png"/&gt; &lt;br/&gt;
⇒ Goal: find a spanning tree with minimum weight sum.   &lt;/p&gt;
&lt;h1 id="2-greedy-algorithm"&gt;2. Greedy Algorithm&lt;/h1&gt;
&lt;p&gt;assumptions for simplification:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;edge weights are distinct   &lt;/li&gt;
&lt;li&gt;graph is connected   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ MST uniquely exists.   &lt;/p&gt;
&lt;h2 id="cut-property"&gt;cut property&lt;/h2&gt;
&lt;p&gt;def. a &lt;strong&gt;cut&lt;/strong&gt; of a graph is a partition of its vertices into 2 non-empty sets. &lt;br/&gt;
def. a &lt;strong&gt;crossing-edge&lt;/strong&gt; (wrt a cut) is an edge connecting vertex from one set to another. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image001-0.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;prop. &lt;/strong&gt;Given any cut, the crossing edges with minimum weight &lt;em&gt;is in the MST&lt;/em&gt;.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image002-0.png"/&gt; &lt;br/&gt;
&lt;em&gt;proof.&lt;/em&gt; &lt;br/&gt;
Given a cut. {S1,S2} are the two set of vertices,  let &lt;code&gt;e&lt;/code&gt; be the min-weighted edge among all crossing-edges.   &lt;/p&gt;
&lt;p&gt;If &lt;code&gt;e&lt;/code&gt; is not in the MST &lt;br/&gt;
   → exist another crossing-edge, &lt;code&gt;f&lt;/code&gt;, in the MST (otherwise not connected) &lt;br/&gt;
    → adding &lt;code&gt;e&lt;/code&gt; to the MST will create a cycle (tree property) &lt;br/&gt;
        → the edge &lt;code&gt;f&lt;/code&gt; will be in this cycle &lt;br/&gt;
        → removing &lt;code&gt;f&lt;/code&gt; and adding &lt;code&gt;e&lt;/code&gt; will give us another spanning tree (!) &lt;br/&gt;
                → this new spanning tree has smaller weight sum ⇒ contradiction, CQFD.   &lt;/p&gt;
&lt;h2 id="greedy-mst-algo"&gt;Greedy MST algo&lt;/h2&gt;
&lt;p&gt;[&lt;strong&gt;algo&lt;/strong&gt; ] Greedy MST  &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;initialize: all edges not selected (colored gray)   &lt;/li&gt;
&lt;li&gt;find any cut with &lt;em&gt;all crossing-edge gray&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;use this cut and select the min-weighted crossing edge (color the edge as black)   &lt;/li&gt;
&lt;li&gt;repeat V-1 times.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;strong&gt;prop.&lt;/strong&gt; the greedy algorithm gets the MST.  &lt;br/&gt;
&lt;em&gt;pf.&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;any selected (black) edges are in the MST (according to the cut property)   &lt;/li&gt;
&lt;li&gt;If we haven't selected V-1 edges → there is always a cut with all crossing-edges gray. (证明algo不会卡死)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(&lt;em&gt;if edge weight not distinct, the proof fails, but can be fixed)&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;efficient implementations&lt;/strong&gt;:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;how to choose the cut each time?   &lt;/li&gt;
&lt;li&gt;how to find min-weighted crossing-edge?    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ Kruskal &amp;amp; Prim   &lt;/p&gt;
&lt;h1 id="3-edge-weighted-graph-api_1"&gt;3. Edge-Weighted Graph API&lt;/h1&gt;
&lt;h2 id="edge-api"&gt;Edge API&lt;/h2&gt;
&lt;p&gt;→ &lt;em&gt;Edge abstraction&lt;/em&gt;: make Edge comparable.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Edge&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;Edge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;w&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;either&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="c1"&gt;// get one of the endpoint of edge (as we are in undirected graph contex here)   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="c1"&gt;// get the other endpoint    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;compareTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;that&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="c1"&gt;// compare by edge weight   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;double&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;weight&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h2 id="edge-weighted-graph-api"&gt;Edge-weighted Graph API&lt;/h2&gt;
&lt;p&gt;adj-list implementation: &lt;code&gt;Bag&amp;lt;Edge&amp;gt;[] adj;&lt;/code&gt;(for undirected graph, each edge appears twice in adj)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;EdgeWeightedGraph&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;EdgeWeightedGraph&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;instead&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;directly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;either&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Edges&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;incident&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Edges&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;(allow self-loops and parallel edges)   &lt;/p&gt;
&lt;h2 id="mst-api"&gt;MST API&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class MST{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    MST(EdgeWeightedGraph G);//compute the MST   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;Edge&amp;gt; edges();// selected edges in the MST   &lt;/span&gt;
&lt;span class="code-line"&gt;    double weight();// sum of all edge weights in MST   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="4-kruskals-algorithm_1"&gt;4.  Kruskal's Algorithm&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;consider edges in ascending order of weight,   &lt;/li&gt;
&lt;li&gt;add the edge to MST &lt;em&gt;unless it creates a cycle&lt;/em&gt;.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;In the running of Kruskal: we have several small connect components and they merge with each other until we get MST.    &lt;/p&gt;
&lt;h2 id="correctness"&gt;correctness&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;prop. &lt;/strong&gt;Kruskal's algo works. &lt;br/&gt;
&lt;em&gt;pf&lt;/em&gt; &lt;br/&gt;
(idea: proove that Kruskal is a special case of the greedy algorithm, ie. how to select the specific cut) &lt;br/&gt;
suppose Kruskal's algo selects(colored black) an edge &lt;code&gt;e=v-w&lt;/code&gt; &lt;br/&gt;
→ select a cut = vertices connected to v in the (constructing) MST; and the rest vertices.  &lt;br/&gt;
    → for this cut, there is no black crossing edges &lt;br/&gt;
        → moreover among all crossing edges of the cut the edge e has the smallest weight!! (by def of Kruskal) CQFD   &lt;/p&gt;
&lt;h2 id="implementation"&gt;implementation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;how to test if adding an edge will create a cycle ?    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;DFS from v to w? → O(V) &lt;br/&gt;
⇒ &lt;strong&gt;Union-Find&lt;/strong&gt; !  O(lg*V) ☺ (almost constant time)   &lt;/p&gt;
&lt;p&gt;if &lt;code&gt;find(v)==find(w)&lt;/code&gt;, then we know adding e will create a cycle.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;considering edges in order? → use a prority queue.    &lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;KruskalMST&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MST&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;KruskalMST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;EdgeWeightedGraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;build&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;--&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;can&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;be&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;optimized&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;O&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;build&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bottom&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;up&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;UF&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;uf&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;UF&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;build&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;UF&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;size&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delMin&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;either&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;uf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;connecte&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;continue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;uf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;union&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;           &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="complexity"&gt;complexity&lt;/h2&gt;
&lt;p&gt;running time: O(ElogE) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;h1 id="5-prims-algorithm_1"&gt;5. Prim's Algorithm&lt;/h1&gt;
&lt;p&gt;since 1930...  &lt;br/&gt;
Idea: start from a vertex and &lt;em&gt;grows the tree &lt;/em&gt;&lt;code&gt;T&lt;/code&gt;&lt;em&gt; to MST.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;Add to the tree T the edge &lt;em&gt;that have exactely one endpoint in T&lt;/em&gt; and with minimum weight,  &lt;/li&gt;
&lt;li&gt;repeat V-1 times.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;In the running of Prim: there is always ONE connnected component .    &lt;/p&gt;
&lt;h2 id="correctness_1"&gt;Correctness&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. Prim's algo works. &lt;br/&gt;
&lt;em&gt;pf.&lt;/em&gt; &lt;br/&gt;
suppose edge e is the min-weighted edge connect a vertex in T with a vertex out of T.  &lt;br/&gt;
→ select the cut = vertices in the tree T; vertices out of T &lt;br/&gt;
→ by def, there is no black crossing edge &lt;br/&gt;
→ e is the min-weighed edge by def of Prim. CQFD   &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;p&gt;challenge: how to find such an edge (connect T and other vertex, with min weight) ? &lt;br/&gt;
⇒ priority queue    &lt;/p&gt;
&lt;h3 id="lazy-implementation"&gt;"lazy" implementation&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;Maintain a PQ of edges that connect T and the rest vertices.    &lt;/li&gt;
&lt;li&gt;&lt;code&gt;e = pq.delMin(), e = v-w&lt;/code&gt;,  if &lt;code&gt;v&lt;/code&gt; and &lt;code&gt;w&lt;/code&gt; are both in T (as edges in pq might become obsolete as T grows) ⇒ &lt;em&gt;just disregard it&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;to maintain the pq: add all incident edges(with other endpoint not in T) of the newly added vertex to pq   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LazyPrimMST&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;LazyPrimMST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;EdgeWeightedGraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;T&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;0&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertex&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;T&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;mst&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;delMin&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;either&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;other&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;continue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;ignore&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;obsolete&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;edges&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="vm"&gt;?&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;newly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;added&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertex&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Edge&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;e&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;e.other(v)&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="n"&gt;pq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Running time: &lt;strong&gt;O(ElgE)&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image002.png"/&gt; &lt;br/&gt;
space: &lt;strong&gt;O(E)&lt;/strong&gt; in worst time.   &lt;/p&gt;
&lt;h3 id="eager-implementation"&gt;"eager" implementation&lt;/h3&gt;
&lt;p&gt;Idea:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;use a &lt;strong&gt;PQ of vertices&lt;/strong&gt;&lt;em&gt;, priority of vertex v := min-weight of edge that connects v to T.&lt;/em&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;strong&gt;[algo]&lt;/strong&gt; &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;Get from pq the vertex &lt;code&gt;v&lt;/code&gt; that is closest to T, add it to T. &lt;br/&gt;
Update pq -- consider &lt;code&gt;v&lt;/code&gt;'s incident edge &lt;code&gt;e=v-w:&lt;/code&gt; &lt;ul&gt;
&lt;li&gt;if w in T → ignore   &lt;/li&gt;
&lt;li&gt;else:   &lt;ul&gt;
&lt;li&gt;if w in pq → add w to pq   &lt;/li&gt;
&lt;li&gt;else → if &lt;code&gt;v-w&lt;/code&gt; has smaller weight than the current priority, update &lt;code&gt;w&lt;/code&gt;'s priority.      &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;repeat till get V-1 edges.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;key implementation component: a &lt;a href="file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_part_II/MinPQ.txt"&gt;MinPQ&lt;/a&gt; that supports priority(key) update.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;IndexMinPQ&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;IndexMinPQ&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;indices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;elements&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;0.&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nb nb-Type"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;key&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nb nb-Type"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;decreaseKey&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;key&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;update&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;key&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;priority&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;element&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delMin&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;size&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;implementation of such a PQ:   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Use same code as standart PQ (maintain a heap[] array). &lt;br/&gt;
Elements are always accessed by "index", in range 0...N-1.
maintain 3 parallel arrays: &lt;code&gt;keys[], pq[], qp[]&lt;/code&gt;:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;keys[i]&lt;/code&gt;: is the priority of element i (the element with index=i)   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;pq[i]&lt;/code&gt;: is the index of the element in the heap position i (ie. in heap[i] is pq[i]th element  )   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;qp[i]&lt;/code&gt;: is heap position of element i  ( ⇔ the ith element is in heap[qp[i]] )   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;to &lt;code&gt;decreaseKey(i,key)&lt;/code&gt;: change &lt;code&gt;keys[i]&lt;/code&gt;, then call &lt;code&gt;siftup(qp[i])&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image004.png"/&gt; &lt;br/&gt;
summery of pq implementations:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;h1 id="6-mst-context_2"&gt;6. MST Context&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;unsolved pb: does a linear MST algo exists?   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(recap: for UF, tarjan has &lt;em&gt;prooved&lt;/em&gt; that linear algo doesn't exist — although Nlg*N is fast enough...) &lt;br/&gt;
@_@... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week2_1/pasted_image007.png"/&gt; &lt;br/&gt;
(这个Yao是清华那个Yao吧?)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Euclidean MST   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Given N points in plane, edge weight := Euclidean distance. (&lt;em&gt;dense graph, E = V2&lt;/em&gt;) &lt;br/&gt;
→ exploit geomerty, O(NlgN)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;clustering   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;k-clustering (~ dist-fcn) &lt;br/&gt;
single-link clustering (def. dist of clusters = dist of 2 closest elements in each cluster) &lt;br/&gt;
→ Kruskal...   &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 1-2 Directed Graphs</title><link href="https://x-wei.github.io/notes/algoII_week1_2.html" rel="alternate"/><published>2015-11-09T00:00:00+01:00</published><updated>2015-11-09T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-09:/notes/algoII_week1_2.html</id><summary type="html">&lt;h1 id="1-intro-to-digraphs"&gt;1. Intro to digraphs&lt;/h1&gt;
&lt;p&gt;Has profound differences wrt undirected graphs.    &lt;/p&gt;
&lt;p&gt;def: digraph &lt;br/&gt;
&lt;em&gt; edges: have directions &lt;br/&gt;
&lt;/em&gt; vertex: distinguish indeg and outdeg   &lt;/p&gt;
&lt;p&gt;digraph pbs:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;path/shortest path   &lt;/li&gt;
&lt;li&gt;topological sort: Can you draw a digraph so that all edges point upwards?   &lt;/li&gt;
&lt;li&gt;strong connectivity: Is there a directed path between all pairs of vertices …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;h1 id="1-intro-to-digraphs"&gt;1. Intro to digraphs&lt;/h1&gt;
&lt;p&gt;Has profound differences wrt undirected graphs.    &lt;/p&gt;
&lt;p&gt;def: digraph &lt;br/&gt;
&lt;em&gt; edges: have directions &lt;br/&gt;
&lt;/em&gt; vertex: distinguish indeg and outdeg   &lt;/p&gt;
&lt;p&gt;digraph pbs:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;path/shortest path   &lt;/li&gt;
&lt;li&gt;topological sort: Can you draw a digraph so that all edges point upwards?   &lt;/li&gt;
&lt;li&gt;strong connectivity: Is there a directed path between all pairs of vertices?   &lt;/li&gt;
&lt;li&gt;transit closure   &lt;/li&gt;
&lt;li&gt;PageRank   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="2-digraph-api"&gt;2. Digraph API&lt;/h1&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class Digraph{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    Digraph(int V);   &lt;/span&gt;
&lt;span class="code-line"&gt;    void addEdge(int v, int w);// edge is directed   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;Interger&amp;gt; adj(int v);// vertices reached by outgoing edges   &lt;/span&gt;
&lt;span class="code-line"&gt;    int V();   &lt;/span&gt;
&lt;span class="code-line"&gt;    Digraph reverse();// &amp;lt;--new methode wrt undirected graph   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;representation: adj-list, ie. an array of bags.  &lt;br/&gt;
&lt;code&gt;Bag&amp;lt;Integer&amp;gt;[] adj;// prec vertices&lt;/code&gt; &lt;/p&gt;
&lt;h1 id="3-digraph-search"&gt;3. Digraph Search&lt;/h1&gt;
&lt;p&gt;BFS and DFS can be applied to digraphs.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;reachability   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;find all vertices reachable from vertex-s.  &lt;br/&gt;
use the same DFS as for undirected graphs.  &lt;br/&gt;
→ application: programme control-flow analyse, garbage collection.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;em&gt;DFS is the basis for a lot of digraph pbs&lt;/em&gt;: 2-satisfiability, Euler path, strongly connected component.    &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;multiple source shortest path:    &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week1_2/pasted_image.png"/&gt; &lt;br/&gt;
⇒ use DFS but &lt;em&gt;enque all vertices in the set&lt;/em&gt;.  &lt;br/&gt;
→ application: web crawler(DFS not suitable for crawling)   &lt;/p&gt;
&lt;h1 id="4-topological-sort"&gt;4. Topological Sort&lt;/h1&gt;
&lt;p&gt;application. precedence schedule, java compiler (cycled inheritance), ...   &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;topo-order&lt;/strong&gt; &lt;br/&gt;
is a permutation of vertices, where for each vertice v→w, w is behind v in the permutation.    &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;DAG&lt;/strong&gt; &lt;br/&gt;
directed acyclic graph. &lt;br/&gt;
&lt;strong&gt;prop. &lt;/strong&gt;for a digraph, topological order exists &lt;em&gt;iff&lt;/em&gt; graph is a DAG.    &lt;/p&gt;
&lt;p&gt;algo: ⇒ use DFS~  &lt;br/&gt;
&lt;em&gt;reverse DFS postorder&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;def.    &lt;strong&gt;postorder&lt;/strong&gt; &lt;br/&gt;
is the order of the vertices that we have &lt;em&gt;finished&lt;/em&gt; (ie. we have visited all reachable vertices from this vertex).   &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;这个以前的blog写过...    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;revPostorder&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;stores&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;reverse&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;post&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;order&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="cm"&gt;/** now we know the vertex v is "finished" **   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    revPostorder.push(v);   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;}   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;public Iterable&amp;lt;Integer&amp;gt; topoOrder(Digraph G){   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    for(int v=0;v&amp;lt;G.V();v++)   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        if(!visited(v)) dfs(G,v);// visit all cc   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    return revPostorder;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="proof"&gt;proof&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;prop. &lt;/strong&gt;reverse post-order of a DAG is in topological order.  &lt;br/&gt;
(这个证明蛮精彩) &lt;br/&gt;
&lt;strong&gt;pf.&lt;/strong&gt; &lt;br/&gt;
for any edge &lt;strong&gt;v→w&lt;/strong&gt;, when &lt;code&gt;dfs(v)&lt;/code&gt; is called:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;case 1: &lt;code&gt;dfs(w)&lt;/code&gt; is called and returned, so w is done before v in post-order;   &lt;/li&gt;
&lt;li&gt;case 2: &lt;code&gt;dfs(w)&lt;/code&gt; is not called, it will be (in)directly get called by &lt;code&gt;dfs(v)&lt;/code&gt;, so &lt;code&gt;dfs(w)&lt;/code&gt; finishes before &lt;code&gt;dfs(v)&lt;/code&gt;;   &lt;/li&gt;
&lt;li&gt;case 3: &lt;code&gt;dfs(w)&lt;/code&gt; is called but NOT returned (ie, w not &lt;em&gt;finished&lt;/em&gt;) → exist path from w to v ⇒ graph is not a DAG! (cycle detection)   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="5-strong-components_1"&gt;5. Strong Components&lt;/h1&gt;
&lt;p&gt;For undirected graphs: connected components can be solved with dfs or UF.    &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;Strongly-connected&lt;/strong&gt; &lt;br/&gt;
v and w are strongly-connected if exist path from v to w and w to v.  &lt;br/&gt;
→ is an equivalent relation.    &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;Strong Component&lt;/strong&gt; &lt;br/&gt;
subset of  V where each pair are strongly-connected.    &lt;/p&gt;
&lt;p&gt;Goal: compute all strong components(&lt;em&gt;scc&lt;/em&gt;) in a digraph.    &lt;/p&gt;
&lt;h2 id="linear-time-dfs-solution-tarjan-1972"&gt;linear time DFS solution: Tarjan (1972)&lt;/h2&gt;
&lt;p&gt;(developed version: a two-pass linear-time algorithm)   &lt;/p&gt;
&lt;p&gt;Intuition: &lt;em&gt;scc for G is the same for G.reverse().&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Kernel DAG&lt;/strong&gt;: contract each scc into a single vertex.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week1_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;Idea:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;compute topological-order in the kernel DAG.   &lt;/li&gt;
&lt;li&gt;run DFS, consider vertices in reverse-topo-order    &lt;/li&gt;
&lt;/ul&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;[Algo]&lt;/strong&gt; &lt;br/&gt;
1. compute topo-order in &lt;code&gt;G.reverse&lt;/code&gt; (just a DFS in the reversed graph) &lt;br/&gt;
2. run DFS in original  &lt;code&gt;G&lt;/code&gt;, &lt;em&gt;visit unmarked vertices in topo-order of G.reverse&lt;/em&gt;. (instead of visiting vertices by their index)   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;⇒ &lt;strong&gt;each time we finish a dfs from a vertex, we get a scc!&lt;/strong&gt; &lt;br/&gt;
太精彩了!!! &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week1_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;proof: tricky, cf book...(貌似Werner课上讲过..)   &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;scc&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;scc&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;index&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;SCC&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;belongs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccCount&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;getSCC&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;1.&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;topo&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;order&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;reverse&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;graph&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;topoOrderGR&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;topoOrder&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;reverse&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mf"&gt;2.&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;run&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;original&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;graph&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;run&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;on&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;using&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;above&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;topo&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="k"&gt;order&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;v&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;topoOrderGR&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="c1"&gt;-- only difference from the standard topo-order algo   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccCount&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;increment&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccCount&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;everytime&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;we&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;done&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;component&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Digraph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;run&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;and&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;touched&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vertices&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;marked&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccId&lt;/span&gt;&lt;span class="err"&gt;'&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;SCC&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;scc&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccCount&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;scc&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sccCount&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms II] Week 1-1 Undirected Graphs</title><link href="https://x-wei.github.io/notes/algoII_week1_1.html" rel="alternate"/><published>2015-11-08T00:00:00+01:00</published><updated>2015-11-08T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-11-08:/notes/algoII_week1_1.html</id><summary type="html">&lt;h1 id="1-intro-to-graphs"&gt;1. Intro to graphs&lt;/h1&gt;
&lt;p&gt;Graph: vertices connected by edges.    &lt;/p&gt;
&lt;p&gt;terminology:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;path&lt;/strong&gt;:  sequence of vertices connected by edges   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;cycle&lt;/strong&gt;: path with same starting and ending vertex   &lt;/li&gt;
&lt;li&gt;two vertices are &lt;strong&gt;connected&lt;/strong&gt;: if there is a path between     &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex of graph problems:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;path: or connectivity   &lt;/li&gt;
&lt;li&gt;shortest path   &lt;/li&gt;
&lt;li&gt;cycle   &lt;/li&gt;
&lt;li&gt;Euler tour (ouii..)   &lt;/li&gt;
&lt;li&gt;Hamilton tour …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;h1 id="1-intro-to-graphs"&gt;1. Intro to graphs&lt;/h1&gt;
&lt;p&gt;Graph: vertices connected by edges.    &lt;/p&gt;
&lt;p&gt;terminology:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;path&lt;/strong&gt;:  sequence of vertices connected by edges   &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;cycle&lt;/strong&gt;: path with same starting and ending vertex   &lt;/li&gt;
&lt;li&gt;two vertices are &lt;strong&gt;connected&lt;/strong&gt;: if there is a path between     &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex of graph problems:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;path: or connectivity   &lt;/li&gt;
&lt;li&gt;shortest path   &lt;/li&gt;
&lt;li&gt;cycle   &lt;/li&gt;
&lt;li&gt;Euler tour (ouii..)   &lt;/li&gt;
&lt;li&gt;Hamilton tour   &lt;/li&gt;
&lt;li&gt;MST   &lt;/li&gt;
&lt;li&gt;bi-connectivity: is there a vertex whose removal disconnects the graph?   &lt;/li&gt;
&lt;li&gt;planarity   &lt;/li&gt;
&lt;li&gt;isomorphism   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="2-graph-api"&gt;2. Graph API&lt;/h1&gt;
&lt;h2 id="graph-representation"&gt;graph representation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;vertex representation:  use integers &lt;em&gt;between 0 and V-1&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;anormalies: self-loop and multiple edges are &lt;em&gt;possible&lt;/em&gt; &lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class Graph{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    Graph(int V);   &lt;/span&gt;
&lt;span class="code-line"&gt;    void addEdge(int v, int w);   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;Integer&amp;gt; adj(int v);   &lt;/span&gt;
&lt;span class="code-line"&gt;    int V();// nb of vertices   &lt;/span&gt;
&lt;span class="code-line"&gt;    int E();// nb of edges   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;print all edges:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week1_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;basic functions:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;degree&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Graph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;g&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;deg&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="nx"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;deg&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;deg&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nx"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nbOfSelfloops&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Graph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;g&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cnt&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;V&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="nx"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;w&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cnt&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cnt&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="edge-representation"&gt;edge representation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;set-of-edge implementation: a list of all edges ⇒ can lead to inefficient implementation   &lt;/li&gt;
&lt;li&gt;adj-matrix implementation: maintain a 2d (V*V) boolean array ⇒ space complexity too heavy   &lt;/li&gt;
&lt;li&gt;adj-list implementation: vertex-indexed array, each array entry is a &lt;code&gt;Bag&lt;/code&gt; (类似桶bucket) ⇒ sutable for sparse graphs   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week1_1/pasted_image001.png"/&gt; &lt;br/&gt;
adj-list implementation:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Graph&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;java&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cannot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;create&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;generic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Bag&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;addEdge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;undirected&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;graph&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week1_1/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-depth-first-search_1"&gt;3. Depth-First Search&lt;/h1&gt;
&lt;p&gt;Tremaux maze exploration: trace back when no unvisited vertices availiable.  &lt;br/&gt;
动画好看... &lt;br/&gt;
DFS goal: systematically search through a graph.  &lt;br/&gt;
&lt;strong&gt;design pattern&lt;/strong&gt;: &lt;em&gt;decouple&lt;/em&gt; graph data and graph processing.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class Paths{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    Path(Graph G, int s);// graph G and source s   &lt;/span&gt;
&lt;span class="code-line"&gt;    boolean hasPathTo(int v);   &lt;/span&gt;
&lt;span class="code-line"&gt;    Iterable&amp;lt;Integer&amp;gt; pathTo(int v);   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;algo:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoII_week1_1/pasted_image003.png"/&gt; &lt;br/&gt;
注意每次访问节点以前就将其mark.    &lt;/p&gt;
&lt;h2 id="implementation"&gt;implementation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;用一个boolean数组&lt;code&gt;visited[]&lt;/code&gt;作为标记   &lt;/li&gt;
&lt;li&gt;为了找到一条具体的路径(ie, 一系列节点), 维护一个&lt;code&gt;prev[]&lt;/code&gt;数组, 存放当前节点是从哪个节点走过来的.    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoII_week1_1/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;DFSpaths&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Paths&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;prev&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;V&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;prev&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;dfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pathTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;prev&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="properties"&gt;properties&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;prop&lt;/strong&gt;. &lt;br/&gt;
DFS visite all edges in time propotional to the sum of their degrees(ie. nb of edges).    &lt;/p&gt;
&lt;h1 id="4-breadth-first-search_1"&gt;4. Breadth-First Search&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;not&lt;/strong&gt; recursive algo. &lt;br/&gt;
&lt;em&gt;maintain a queue, add to queue for all vertices not-marked.&lt;/em&gt; &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;use &lt;code&gt;visited[]&lt;/code&gt; to mark vertices   &lt;/li&gt;
&lt;li&gt;use a &lt;code&gt;prev[]&lt;/code&gt; array to get explicit path   &lt;/li&gt;
&lt;li&gt;use a &lt;code&gt;dist[]&lt;/code&gt; array to record the shortest dist from v to source (can use &lt;code&gt;dist&lt;/code&gt; to replace &lt;code&gt;visited&lt;/code&gt;)   &lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;bfs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Graph&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;prev&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;G.V()&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;dequeue&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;w&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;adj&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;prev&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;enqueue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;w&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="property"&gt;property&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;prop.&lt;/strong&gt; &lt;br/&gt;
BFS computes the shortest path from s to all vertices using time propotional to E+V.    &lt;/p&gt;
&lt;p&gt;intuition: BFS examines nodes by increasing distance    &lt;/p&gt;
&lt;h1 id="5-connected-components_1"&gt;5. Connected Components&lt;/h1&gt;
&lt;p&gt;dealing with connectivity(equivalence) queries ⇒ answer in constant time (with &lt;em&gt;preprocessing&lt;/em&gt;).    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;CC&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;connected&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;w&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;// nb of CCs   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;id&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//id for a CC   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;⇒ Union-Find ? ⇒ &lt;em&gt;Use DFS!!&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;def. &lt;em&gt;connected component&lt;/em&gt; is a maximal set of connected vertices.    &lt;/p&gt;
&lt;p&gt;algo: for each unmarked vertex, run dfs(with increasing cc id)... &lt;br/&gt;
after the preprocessing, we can get the array &lt;code&gt;id[]&lt;/code&gt; and cc count &lt;code&gt;cnt&lt;/code&gt;...   &lt;/p&gt;
&lt;h1 id="6-graph-challenges"&gt;6. Graph Challenges&lt;/h1&gt;
&lt;p&gt;some typical pbs &lt;br/&gt;
&lt;strong&gt;pb1. bipartite graph&lt;/strong&gt; &lt;/p&gt;
&lt;p&gt;Can we  divide vertices into 2 subsets, where all edge go from one subset to other.  &lt;br/&gt;
⇒ can be done with dfs. &lt;em&gt;cf. booksite&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;pb2. cycle detection&lt;/strong&gt; &lt;br/&gt;
⇒ simple using dfs.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;pb3. Euler cycle&lt;/strong&gt; &lt;br/&gt;
Find a cycle that uses all edges exactely once.  &lt;br/&gt;
[Euler] a graph is Eulerian &lt;strong&gt;iff&lt;/strong&gt; all vertices have even degree.  &lt;br/&gt;
⇒ typical diligent algo students can do. &lt;em&gt;cf. booksite&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;pb4. Hamilton cycle&lt;/strong&gt; &lt;br/&gt;
Find cycle that visits each vertex exactly once.  &lt;br/&gt;
⇒ intractable (typical NP-complete pb)   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;pb5. isomorphism of graphs&lt;/strong&gt; &lt;br/&gt;
Are two graphs identical except for vertex names? &lt;br/&gt;
⇒ no one knows...    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;pb6. planary graph&lt;/strong&gt; &lt;br/&gt;
Lay out a graph in the plane without crossing edges? &lt;br/&gt;
⇒ expert level. exists linear time algo based on DFS by Tarjan, but too complicated.    &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>最短路径三剑客: Floyd, Dijkstra, Bellman</title><link href="https://x-wei.github.io/tech/shortest-path-summary.html" rel="alternate"/><published>2015-10-18T17:00:00+02:00</published><updated>2015-10-18T17:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-10-18:/tech/shortest-path-summary.html</id><summary type="html">&lt;p&gt;weighted graph的最短路径问题有三个非常有名的算法, 分别以三个大牛的名字命名, 今天用尽量简洁的篇幅一一介绍.    &lt;/p&gt;
&lt;p&gt;简单起见(这回只写伪代码好了), 对于图的定义如下:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;node …&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;p&gt;weighted graph的最短路径问题有三个非常有名的算法, 分别以三个大牛的名字命名, 今天用尽量简洁的篇幅一一介绍.    &lt;/p&gt;
&lt;p&gt;简单起见(这回只写伪代码好了), 对于图的定义如下:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;node index = &lt;code&gt;{1,2,...,n}&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;&lt;code&gt;e[u,v]&lt;/code&gt; = distance of edge(u,v); if (u,v) is not an edge, &lt;code&gt;e[u,v]=INF&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;令N=点的数量, M=边的数量   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="floyd-warshall"&gt;任意两点最短路径: Floyd-Warshall&lt;/h1&gt;
&lt;p&gt;Floyd算法解决的问题是: 对于&lt;strong&gt;任意&lt;/strong&gt;两个节点&lt;code&gt;s&lt;/code&gt;(source)和&lt;code&gt;t&lt;/code&gt;(target), 求s到达t的最短路径.    &lt;/p&gt;
&lt;p&gt;Floyd算法的思想是动态规划:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;定义&lt;code&gt;d(i,j,k)&lt;/code&gt;为点i到点j之间, &lt;strong&gt;只允许借道节点1...k的最短路径&lt;/strong&gt; &lt;/li&gt;
&lt;li&gt;初始化: &lt;code&gt;d(i,j,0)=e[i,j]&lt;/code&gt;(即i到j之间不经由其他任何中转节点的最短路径)   &lt;/li&gt;
&lt;li&gt;更新dij的公式就是: &lt;code&gt;d(i,j,k)=min( d(i,j,k-1), d(i,k-1,k-1)+e[k,j])&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;更新n次   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;每次更新dij的意思就是: 现在从i到j可以经过节点k了, 那么看一下ij之间从k这个点经过的话(i → k → j 这条路)能不能缩短dij.    &lt;/p&gt;
&lt;p&gt;i到j最短路径最终就是: &lt;code&gt;d(i,j,n)&lt;/code&gt; 即i到j的路程可以经过1~n中的任何中转节点.    &lt;/p&gt;
&lt;p&gt;伪代码特别短(其实真代码也一样短....):    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]:&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;initialize&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;d&lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;e&lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;~&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;n&lt;/span&gt;:&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;relax&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;times&lt;/span&gt;:&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]:&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;d&lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;min&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;d&lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;],&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;d&lt;/span&gt;[&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="nv"&gt;k&lt;/span&gt;]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;e&lt;/span&gt;[&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="nv"&gt;j&lt;/span&gt;]&lt;span class="ss"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;核心代码只有最后三行... 运行结束后&lt;code&gt;d[i,j]&lt;/code&gt;就保存着任意i和j之间的最短路径长度.  &lt;br/&gt;
程序主循环n次, 每次要处理遍历所有的ij组合, 所以复杂度是&lt;strong&gt;O(N^3)&lt;/strong&gt;.    &lt;/p&gt;
&lt;h1 id="dijkstra"&gt;单源最短路径: Dijkstra&lt;/h1&gt;
&lt;p&gt;Dijkstra算法解决的问题是: 没有负权边的情况下, 从&lt;strong&gt;源节点&lt;/strong&gt;&lt;code&gt;s&lt;/code&gt;到其他任意节点&lt;code&gt;t&lt;/code&gt;的路径长度.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;维护一个dist数组, dist[i]就表示(目前为止)s到i的最短距离.    &lt;/li&gt;
&lt;li&gt;对于每个元素, &lt;strong&gt;标记&lt;/strong&gt;是否其dist是否已经确定不再更改(或者说维护两个集合: 一个集合的dist确定, 另一个未确定).    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Dijkstra算法是一种贪心策略: 每次在未确定最短路径的节点里挑选距离s最近的那个点, 把这个点标记为已经确定dist, 然后对从这个点出发的边进行松弛.    &lt;/p&gt;
&lt;p&gt;为了标记每个点, 这里用一个bool数组表示: &lt;code&gt;determined[i]&lt;/code&gt;为true表示i的dist已经是最短路程, 为false表示还不确定.    &lt;/p&gt;
&lt;p&gt;算法如下:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;初始化&lt;code&gt;dist[i] = e[s,i]&lt;/code&gt;, &lt;code&gt;determined[i]&lt;/code&gt;全为false   &lt;/li&gt;
&lt;li&gt;在dist未确定的元素里(&lt;code&gt;determined[i]==false&lt;/code&gt;)寻找一个dist最小的节点&lt;code&gt;u:&lt;/code&gt; &lt;ul&gt;
&lt;li&gt;标记&lt;code&gt;u&lt;/code&gt;的dist已经确定&lt;code&gt;determined[i]=true&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;用u的所有出边进行松弛: s到i如果经过(u,i)这条边会不会变近? &lt;code&gt;dist[i] = min(dist[i], dist[u]+e[u,i])&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;重复循环直到所有的点都确定dist(or 重复N遍即可: &lt;em&gt;每次只会确定一个新的节点的距离&lt;/em&gt;)   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;伪代码:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;~&lt;/span&gt;&lt;span class="nl"&gt;n&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s,i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;determined&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;false&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;loop&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;times&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;argmin&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;among&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;determined&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="k"&gt;false&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;determined&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;determine&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;one&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;at&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;each&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;loop&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;such&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u,v&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;&lt;/span&gt;&lt;span class="nl"&gt;INF&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u,v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;以上代码的复杂度为O(N^2), 不过如果用堆来优化寻找最近的u的距离, 复杂度可以变得更低.    &lt;/p&gt;
&lt;h1 id="bellman-ford"&gt;有负权边的单源最短路径: Bellman-Ford&lt;/h1&gt;
&lt;p&gt;Dijkstra算法的缺点在于不能处理边长为负数的情况, 而这就是Bellman-Ford算法解决的.    &lt;/p&gt;
&lt;p&gt;Bellman算法也是一种动态规划(动态规划这个东西就是Bellman提出来的):    &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;定义&lt;code&gt;d(i,k)&lt;/code&gt;为源点s到i&lt;strong&gt;最多经过k条边的&lt;/strong&gt;最短距离   &lt;/li&gt;
&lt;li&gt;初始化: &lt;code&gt;d(i,1)=e[s,i]&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;每次更新di的公式: &lt;code&gt;for all (u,v): d(v,k)=min( d(v,k-1), d(u,k-1)+e[u,v] )&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;更新n-1次   &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;为什么是更新n-1次? 因为s到i的最短路径至多只有n-1条边(即s到i的路径经过了所有n个点).  &lt;br/&gt;
注意每次更新, 需要把&lt;strong&gt;所有的边&lt;/strong&gt;试一遍: 看看用每条边(u,v)能不能松弛dv.    &lt;/p&gt;
&lt;p&gt;伪代码:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;~&lt;/span&gt;&lt;span class="nl"&gt;n&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;s,i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;loop&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;times&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;such&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;that&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u,v&lt;/span&gt;&lt;span class="o"&gt;]&amp;lt;&lt;/span&gt;&lt;span class="nl"&gt;INF&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;u,v&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;核心代码也是最后三行... 太tm精妙了!!    &lt;/p&gt;
&lt;p&gt;外层循环N-1次, 内层循环M次, 所以代码的复杂度是O(NM).   &lt;/p&gt;
&lt;h1 id="more"&gt;More&lt;/h1&gt;
&lt;p&gt;以下问题有空再写...   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;negative cycle   &lt;/li&gt;
&lt;li&gt;A*   &lt;/li&gt;
&lt;/ul&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>深度优先搜索(DFS)小结</title><link href="https://x-wei.github.io/tech/dfs-summary.html" rel="alternate"/><published>2015-10-18T00:00:00+02:00</published><updated>2015-10-18T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-10-18:/tech/dfs-summary.html</id><summary type="html">&lt;p&gt;今天总结一下也许是搜索问题里最重要的算法: DFS !    &lt;/p&gt;
&lt;p&gt;由于树可以看成是一个graph, 这里还是只写对于graph的DFS算法. Graph类的定义还是用每一个节点保存邻居信息:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class GraphNode{      &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    int val;      &lt;/span&gt;
&lt;span class="code-line"&gt;    List&amp;lt;GraphNode&amp;gt; neighbors …&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;p&gt;今天总结一下也许是搜索问题里最重要的算法: DFS !    &lt;/p&gt;
&lt;p&gt;由于树可以看成是一个graph, 这里还是只写对于graph的DFS算法. Graph类的定义还是用每一个节点保存邻居信息:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class GraphNode{      &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    int val;      &lt;/span&gt;
&lt;span class="code-line"&gt;    List&amp;lt;GraphNode&amp;gt; neighbors;      &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;为了防止重复, 仍然用一个HaseSet记录走过的节点:    &lt;/p&gt;
&lt;p&gt;&lt;code&gt;HasheSet&amp;lt;GraphNode&amp;gt; visited = new HasheSet&amp;lt;GraphNode&amp;gt;();&lt;/code&gt; &lt;/p&gt;
&lt;h2 id="recursive-dfs"&gt;Recursive DFS&lt;/h2&gt;
&lt;p&gt;首先写递归版本的DFS, DFS就是一条路走到底, 不撞南墙不回头, 所以递归写起来很自然: 每到一个节点, 标记其已经访问过了, 然后对于邻居里面没有访问的节点继续递归进行DFS.    &lt;/p&gt;
&lt;p&gt;递归的DFS代码非常简洁:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;DFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;System.out.println(nd.val)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;visited.add(nd)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;neighbors&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;DFS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;虽然这个算法很短, 但是它非常重要, 回溯算法(backtracking)其实就相当于在问题的求解域做一个dfs. 另外拓扑排序也是基于递归dfs进行一点点修改.    &lt;/p&gt;
&lt;h2 id="non-recursive-dfs"&gt;Non-recursive DFS&lt;/h2&gt;
&lt;p&gt;非递归版本的dfs同样很重要, 因为毕竟非递归的版本效率高一些, 另外这个算法和bfs非常相似, 只不过把队列queue换成了栈stack而已:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;DFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;start&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;Stack&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;Stack&amp;lt;GraphNode&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;q.push(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;visited.add(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;while(!s.empty()){&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;cur&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;s.pop()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;System.out.println(cur.val)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cur&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;       &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="err"&gt;visited.add(next)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;mark&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;when&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;adding&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;stack!&lt;/span&gt;&lt;span class="w"&gt;       &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nt"&gt;while&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;同样要注意的一点就是在把一个节点入栈的时刻就将其标记为已访问.    &lt;/p&gt;
&lt;h2 id="for-trees-dfs-with-depth"&gt;(for Trees) DFS with depth&lt;/h2&gt;
&lt;p&gt;和上次&lt;a href="http://x-wei.github.io/bfs-summary.html"&gt;bfs&lt;/a&gt;一样, &lt;strong&gt;对于树而言&lt;/strong&gt;, 在dfs搜索的过程中也可以记录该节点所在的depth.    &lt;/p&gt;
&lt;p&gt;非递归版本的程序就是用一个和上面&lt;code&gt;s&lt;/code&gt;平行的栈记录深度, 程序和"BFS with distance"很像. 递归版本只要在函数签名里加上一个depth的参数即可. 这两个实现都很简单, 就不写了.    &lt;/p&gt;
&lt;p&gt;注意这个只对于树有意义, 对一个图而言没有depth一说...    &lt;/p&gt;
&lt;h2 id="dfs-for-binary-tree-preorder-traversal"&gt;DFS for binary tree: Preorder traversal&lt;/h2&gt;
&lt;p&gt;dfs另一个有用的性质是: 对于&lt;strong&gt;二叉树&lt;/strong&gt;而言, dfs得到的节点顺序正是其前序遍历(preorder traversal)的顺序.    &lt;/p&gt;
&lt;p&gt;其实前序遍历的定义就相当于是一个递归版本的dfs了:  &lt;br/&gt;
&lt;code&gt;[preorder(node)] = node.val + [preorder(node.left)] + [preorder(node.right)]&lt;/code&gt; &lt;/p&gt;
&lt;h2 id="dfs-with-path"&gt;DFS with path&lt;/h2&gt;
&lt;p&gt;如果在访问到某一个节点的时候想同时获得到该点的路径, 其实也不麻烦.    &lt;/p&gt;
&lt;p&gt;对于递归版本的dfs而言, 可以在参数里面用一个List记录到当前节点的路径.    &lt;/p&gt;
&lt;p&gt;非递归的版本的话... 貌似不是很trival, 需要对stack做好维护, 可能需要一个hashmap什么的... 以后有空了再写写.    &lt;/p&gt;
&lt;h2 id="cycle-detection"&gt;Cycle Detection&lt;/h2&gt;
&lt;p&gt;判断一个有向图是否存在回路是一个非常重要的问题, 简单修改dfs就可以做到了.    &lt;/p&gt;
&lt;p&gt;在递归版本的dfs里, 我们对每一个点改为&lt;strong&gt;三种标记&lt;/strong&gt;:  &lt;br/&gt;
&lt;em&gt;未访问过(0), 正在访问其邻居节点(1), 已经访问完该节点以及所有该节点可以到达的节点(2)&lt;/em&gt;.    &lt;/p&gt;
&lt;p&gt;什么时候会出现回路呢? &lt;em&gt;就是当前节点v的一个邻居u的状态为1的时候&lt;/em&gt;. 因为该节点状态为1, 即还没有把它以后的节点全部遍历, 所以当前节点v肯定可以从u到达, 而现在又可以从v到达u, 所以构成一个回路.    &lt;/p&gt;
&lt;p&gt;为了表示一个节点的三种状态, 我们把visited的定义改一下, 定义为一个hashmap:     &lt;br/&gt;
&lt;code&gt;HasheMap&amp;lt;GraphNode, Boolean&amp;gt; visited = new HasheMap&amp;lt;GraphNode, Boolean&amp;gt;();&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;节点不在visited表示还未访问过, 节点对应为false表示正在访问, 节点对应为true表示已经访问该节点以及所有可以从它到达的节点.    &lt;/p&gt;
&lt;p&gt;写一下代码:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;DFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;visited.put(nd,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;false)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;mark&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;status-1&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;neighbors&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;DFS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;if(visited.get(next)==false)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;found&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;cycle&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;System.out.println("Cycle&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;detected!!!")&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;now&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;touchable&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nodes&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;visited&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;visited&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;put&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;true&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;mark&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;status-2&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;非递归版本的话貌似也不很容易, 暂时不写了, 以后有空了考虑一下...   &lt;/p&gt;
&lt;h2 id="topology-sort"&gt;Topology Sort&lt;/h2&gt;
&lt;p&gt;这一节(以及上一节)参考这个非常棒的视频: &lt;a href="https://class.coursera.org/algo-003/lecture/52"&gt;https://class.coursera.org/algo-003/lecture/52&lt;/a&gt; &lt;/p&gt;
&lt;p&gt;拓扑排序是一个dfs的应用, 所谓拓扑排序是指在一个DAG(有向无回路图)里给每个节点定义一个顺序(v1...vn), 使得按照这个顺序遍历的节点, 每一个节点vi都是之前遍历过的的节点(v1 ~ vi-1)所指向的(或没有任何其他节点指向的).    &lt;/p&gt;
&lt;p&gt;好像还没说清楚... 拓扑排序的一个应用就是对于各种依赖性(比如学习课程A需要先学习过课程B)组成的图寻找一个节点遍历的顺序使其可行.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;propositions&lt;/strong&gt;:    &lt;/p&gt;
&lt;blockquote&gt;
&lt;ul&gt;
&lt;li&gt;拓扑排序的结果不唯一.    &lt;/li&gt;
&lt;li&gt;有回路的图不存在拓扑顺序.   &lt;/li&gt;
&lt;li&gt;如果一个节点没有出边, 那么它可以放在拓扑排序的最后面(没有节点以来它).   &lt;/li&gt;
&lt;li&gt;如果一个节点没有入边, 那么它可以放在拓扑排序的最后面.    &lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;简单修改一下递归的dfs就可以处理拓扑排序: 维护一个计数器&lt;code&gt;K&lt;/code&gt;(初始化为n=所有节点数), 每当一个点已经遍历完毕(所有通过这个点可以到达的点都已经被走过)以后, 就把这个点的顺序设为K, 同时减少K.    &lt;/p&gt;
&lt;p&gt;就用一个HashMap来为每个节点关联一个序号好了:  &lt;br/&gt;
&lt;code&gt;HasheMap&amp;lt;GraphNode, Integer&amp;gt; order = new HasheMap&amp;lt;GraphNode, Integer&amp;gt;();&lt;/code&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;DFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;      &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;neighbors&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;DFS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;touchable&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nodes&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;from&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;visited&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nt"&gt;order&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;put&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;K--&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;是不是特别简单, 太神奇了!    &lt;/p&gt;
&lt;p&gt;上面只是对于一个点进行的, 为了给所有点拓扑排序, 只要从一个没有出边的节点出发进行遍历, 一直运行到所有的节点都已经访问过为止.    &lt;/p&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>广度优先搜索(BFS)小结</title><link href="https://x-wei.github.io/tech/bfs-summary.html" rel="alternate"/><published>2015-10-08T00:00:00+02:00</published><updated>2015-10-08T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-10-08:/tech/bfs-summary.html</id><summary type="html">&lt;p&gt;今天总结一下广度优先搜索(BFS). BFS是树/图的遍历的常用算法之一, 对于没有边权重的图来说可以计算最短路径.  &lt;br/&gt;
由于树的BFS只是图的BFS的一种特殊情况, 而 …&lt;/p&gt;</summary><content type="html">&lt;p&gt;今天总结一下广度优先搜索(BFS). BFS是树/图的遍历的常用算法之一, 对于没有边权重的图来说可以计算最短路径.  &lt;br/&gt;
由于树的BFS只是图的BFS的一种特殊情况, 而且比较简单不需要visited标记, 这里只写一下图的BFS好了.  &lt;br/&gt;
先定义一个Graph类, 这里在每一个节点保存邻居信息:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class GraphNode{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    int val;   &lt;/span&gt;
&lt;span class="code-line"&gt;    List&amp;lt;GraphNode&amp;gt; neighbors;   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="bfs-for-treesgraphs"&gt;BFS for trees/graphs&lt;/h2&gt;
&lt;p&gt;图的遍历需要注意不走重复节点, 所以需要一个HashSet(名字叫visited)来保存哪些节点已经访问过了. 需要注意的是, &lt;em&gt;在把一个节点放进队列queue的时刻就要把它放进visited&lt;/em&gt;, 而不是在队列里取出来的时刻再放.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;BFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;start&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;LinkedList&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;LinkedList&amp;lt;GraphNode&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;HasheSet&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;HasheSet&amp;lt;GraphNode&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;q.push(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;visited.add(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;while(!q.empty()){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;cur&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;q.poll()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;System.out.println(cur.val)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cur&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="err"&gt;visited.add(next)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;mark&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;when&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;adding&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;queue!&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nt"&gt;while&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="bfs-with-distance"&gt;BFS with distance&lt;/h2&gt;
&lt;p&gt;在BFS的同时我们可以记录从start节点到当前node的距离, 方法是把一个距离信息同时入队(封装一个&lt;code&gt;Pair&amp;lt;GraphNode, Integer&amp;gt;&lt;/code&gt;), 或者使用一个与queue&lt;em&gt;平行&lt;/em&gt;的队列保存距离信息.  &lt;br/&gt;
在上面的代码中, 加入:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="c1"&gt;//...   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;LinkedList&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;distq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LinkedList&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Integer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="n"&gt;distq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="c1"&gt;// distance from start to start   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="c1"&gt;//...   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="c1"&gt;// in the while(!q.empty()) loop:    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nb"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;distq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;poll&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="c1"&gt;//get distance from start to current node   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;node&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;children&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;distq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="c1"&gt;// distance from start to next node   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="c1"&gt;//...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;对于Tree的情况来说, 这里的dist其实就是当前节点的深度depth.    &lt;/p&gt;
&lt;h2 id="properties"&gt;properties&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;性质1:&lt;/strong&gt; &lt;br/&gt;
每个节点node的distance都是node距离起始点start的最短距离.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;性质2:&lt;/strong&gt; &lt;br/&gt;
距离start近的节点(depth浅的节点)一定比距离start远的节点早被访问到.    &lt;/p&gt;
&lt;p&gt;这是对一个树BFS的时候节点的访问顺序:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/bfs-summary/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h2 id="bfs-by-layer"&gt;BFS "by layer"&lt;/h2&gt;
&lt;p&gt;参考上面的性质, 可以一次处理"一层"的节点, "一层"的意思是指所有节点距离start的距离相同. 代码在while循环里不是一次poll一个节点, 而是一次把queue的内容处理完, 然后换新的queue进入下一次while循环. 代码重新写一下:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;BFS&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;start&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;ArrayList&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;ArrayList&amp;lt;Tree&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;HasheSet&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;visited&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;HasheSet&amp;lt;GraphNode&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;q.push(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;visited.add(start)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;while(!q.empty()){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;ArrayList&amp;lt;GraphNode&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;newq&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;ArrayList&amp;lt;Tree&amp;gt;()&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;create&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;a&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;queue&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cur&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;deal&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nodes&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;queue&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;out&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;cur&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="s2"&gt;", "&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nodes&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;are&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;of&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;same&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;distance/depth&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;for(GraphNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cur&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="n"&gt;visited&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;newq&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;next&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="err"&gt;visited.add(next)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;out&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;println&lt;/span&gt;&lt;span class="o"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nt"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;newq&lt;/span&gt;&lt;span class="o"&gt;;//&lt;/span&gt;&lt;span class="nt"&gt;replace&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;newq&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nt"&gt;while&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;以上程序每次打印一行, 第i行包括了距start距离为i的所有节点.  &lt;br/&gt;
由于这样的话每次不必在队首poll出元素(而是依次处理所有queue的元素), 所以可以改用ArrayList. 此时while循环里的不变量是: 所有q里面的节点距离start的距离都相同.    &lt;/p&gt;
&lt;h2 id="complexity"&gt;complexity&lt;/h2&gt;
&lt;p&gt;假设一个图有N个节点和M条边, BFS会走遍所有节点, 时间是O(N), 然后由于每个节点会检查所有的出边, 最终所有的边都会被检查过, 时间是O(M), 所以BFS的时间复杂度是&lt;strong&gt;O(N+M)&lt;/strong&gt;.    &lt;/p&gt;
&lt;p&gt;队列里面最多可能存放所有节点, 空间复杂度为&lt;strong&gt;O(N)&lt;/strong&gt;.    &lt;/p&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>Mindmap of algorithms &amp; data structures</title><link href="https://x-wei.github.io/tech/algo-ds-mindmap.html" rel="alternate"/><published>2015-10-05T00:00:00+02:00</published><updated>2015-10-05T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-10-05:/tech/algo-ds-mindmap.html</id><content type="html">&lt;p&gt;Here is a mindmap of the common algorithms and data structures, it can give an overview of the algorithmic terms.    &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algo-ds-mindmap/Algo%20%26%20DS.png"/&gt; &lt;/p&gt;
&lt;p&gt;I shall update its content later on. And maybe write some blog entries on some of the items.   &lt;/p&gt;
&lt;p&gt;This mindmap is drawn using &lt;a href="http://www.xmind.net/"&gt;xmind&lt;/a&gt;.   &lt;/p&gt;</content><category term="tech"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 6 Hash Tables</title><link href="https://x-wei.github.io/notes/algoI_week6.html" rel="alternate"/><published>2015-09-01T00:00:00+02:00</published><updated>2015-09-01T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-09-01:/notes/algoI_week6.html</id><summary type="html">&lt;p&gt;&lt;em&gt;Can we do better than BST if we do not need ordered operations ?&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;(No compare methods, use equals method)   &lt;/p&gt;
&lt;p&gt;Idea: save items in an array.  &lt;br/&gt;
&lt;strong&gt;Hash function&lt;/strong&gt;: method for calclulating the array index of  a key.    &lt;/p&gt;
&lt;p&gt;Issues:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;computing hash function   &lt;/li&gt;
&lt;li&gt;equality tests   &lt;/li&gt;
&lt;li&gt;collision resolution   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;Classic space-time tradeoff.&lt;/em&gt; &lt;/p&gt;
&lt;h1 id="1-hash-functions"&gt;1. Hash Functions …&lt;/h1&gt;</summary><content type="html">&lt;p&gt;&lt;em&gt;Can we do better than BST if we do not need ordered operations ?&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;(No compare methods, use equals method)   &lt;/p&gt;
&lt;p&gt;Idea: save items in an array.  &lt;br/&gt;
&lt;strong&gt;Hash function&lt;/strong&gt;: method for calclulating the array index of  a key.    &lt;/p&gt;
&lt;p&gt;Issues:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;computing hash function   &lt;/li&gt;
&lt;li&gt;equality tests   &lt;/li&gt;
&lt;li&gt;collision resolution   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;Classic space-time tradeoff.&lt;/em&gt; &lt;/p&gt;
&lt;h1 id="1-hash-functions"&gt;1. Hash Functions&lt;/h1&gt;
&lt;p&gt;Goal: scramble the keys uniformly to produce a table index.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;effcient to compute   &lt;/li&gt;
&lt;li&gt;all indices are equally likely for any key   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;challenge: need different approach for different key types.    &lt;/p&gt;
&lt;h2 id="javas-hashing"&gt;Java's hashing&lt;/h2&gt;
&lt;p&gt;All java object has a methode &lt;code&gt;int hashCode()&lt;/code&gt; &lt;br/&gt;
requirement:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if x.equals(y) ⇒ x.hashCode()==y.hashCode()   &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;(hopefully) if x.equals(y)==false ⇒ x.hashCode!=y.hashCode()   &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Default implementation: &lt;em&gt;memory address&lt;/em&gt; for x.    &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;Custom implementations for standard types: Integer, Double, String, File, URL, Date...   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image.png"/&gt; &lt;br/&gt;
Strings: Horner's method — compute a polynome.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image001.png"/&gt; &lt;br/&gt;
recipe for user-defined types:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h2 id="modeular-hasing"&gt;Modeular hasing&lt;/h2&gt;
&lt;p&gt;(hash code VS hash function)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;Hash code&lt;/em&gt;: 32-bit integer between -2^31 and 2^31-1 &lt;em&gt;(can be negative!!)&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;&lt;em&gt;Hash function&lt;/em&gt;: integer between 0 and M-1 (used directly as array index, should &amp;gt;=0)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;BUG code:&lt;/strong&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hash&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;hashCode&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="nv"&gt;M&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;→ bug: &lt;em&gt;number returned can be negative !&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;1-in-billion bug code:&lt;/strong&gt; &lt;br/&gt;
&lt;code&gt;return Math.abs(k.hashCode()) % M;&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;→ bug: Math.abs() returns negative numbers for -2^31 &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;correct code:&lt;/strong&gt; &lt;br/&gt;
just take the first 31 bits: x&amp;amp;0x7fffffff &lt;br/&gt;
&lt;code&gt;return k.hashCode()&amp;amp;0x7fffffff % M;&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;另一个hash的思路是用random(用hashcode作为随机种子)   &lt;/p&gt;
&lt;h2 id="uniform-hasing-assumption"&gt;uniform hasing assumption&lt;/h2&gt;
&lt;p&gt;each key is equally likely to hash to an integer between 0 and M-1   &lt;/p&gt;
&lt;p&gt;一些数学结论:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-separate-chaining_1"&gt;2. Separate Chaining&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;one strategy for collision resolution.&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;idea&lt;/strong&gt;: Using a table of size M &amp;lt; N,  build a list for each of the table positions.    &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;SeparateChainingHashST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;97&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;97&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;Object&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;no&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;generic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;creation&lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nxt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;hashCode&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="mh"&gt;0x7fffffff&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;equals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nf"&gt;cast&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;equals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;st&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;注意内部类Node里用的是Object — 因为不能声明generic array.    &lt;/p&gt;
&lt;h2 id="analysis"&gt;analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt; &lt;br/&gt;
Under the assumption of uniform hashing, the number of keys in a list is within a constant factor to N/M.  &lt;br/&gt;
&lt;em&gt;proof.&lt;/em&gt; &lt;br/&gt;
binominal distribution.   &lt;/p&gt;
&lt;p&gt;M times faster than sequential search &lt;br/&gt;
→ typical choice: M ~ N/5   &lt;/p&gt;
&lt;h1 id="3-linear-probing_1"&gt;3. Linear Probing&lt;/h1&gt;
&lt;p&gt;Another approch for collision resolution.    &lt;/p&gt;
&lt;p&gt;idea: &lt;strong&gt;open addressing&lt;/strong&gt; &lt;br/&gt;
Use an array of size &lt;strong&gt;M&amp;gt;N&lt;/strong&gt;, when a key collides, &lt;em&gt;find next open slot&lt;/em&gt;.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;insert: when occupied, move pointer until got open slot   &lt;/li&gt;
&lt;li&gt;search: when not found, move pointer until find or reach open slot   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;delete&lt;/em&gt;: set key to null, then for all items behind this key: set to null, then insert this key......   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;array M &lt;em&gt;must&lt;/em&gt; be larger than N ⇒ array resizing is necessary.    &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LinearProbingHashST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Object&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;cannot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;use&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;generic&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;array&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Object&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vals&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(;&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;equals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="n"&gt;vals&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;vals&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;hash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(;&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]!=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;M&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;equals&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="n"&gt;vals&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;ugly&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;cast&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="cluster"&gt;cluster&lt;/h2&gt;
&lt;p&gt;def. &lt;strong&gt;cluster&lt;/strong&gt; &lt;br/&gt;
A contiguous block of items.    &lt;/p&gt;
&lt;p&gt;New keys are more likely to hash into a cluster.    &lt;/p&gt;
&lt;p&gt;Knuth parking pb:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image008.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image010.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image009.png"/&gt; &lt;br/&gt;
(当年Knuth就是在证明了这个以后决定写那套书)   &lt;/p&gt;
&lt;p&gt;Typical choice: &lt;strong&gt;N/M ~ 1/2&lt;/strong&gt; (3/2 for search hit and 5/2 for search miss)   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-hash-table-context_1"&gt;4. Hash Table Context&lt;/h1&gt;
&lt;p&gt;widely used in applicataions.    &lt;/p&gt;
&lt;p&gt;cost for computing hash VS cost for searching:  &lt;br/&gt;
hashCode() for strings in java 1.1: exemain only 8-9 evenly spaced characters to save time. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;uniform hashing assumption: performance not guaranteed... &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;one-way hash functions&lt;/strong&gt; &lt;br/&gt;
Hard to find a key that hash to a desired value, or 2 keys having the same hash value.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image015.png"/&gt; &lt;br/&gt;
used for fingurprints or store passwords, but too expensive for ST implementations.    &lt;/p&gt;
&lt;h2 id="seperate-chaining-vs-linear-probing"&gt;Seperate chaining VS linear probing&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;h2 id="variations"&gt;variations&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;h2 id="st-choice-hash-tables-vs-balanced-search-trees"&gt;ST choice: hash tables VS balanced search trees&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week6/pasted_image018.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 5-2 Geometric Applications of BSTs</title><link href="https://x-wei.github.io/notes/algoI_week5_2.html" rel="alternate"/><published>2015-08-29T00:00:00+02:00</published><updated>2015-08-29T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-29:/notes/algoI_week5_2.html</id><summary type="html">&lt;h1 id="1-1d-range-search"&gt;1. 1d Range Search&lt;/h1&gt;
&lt;p&gt;Goal: &lt;em&gt;intersections&lt;/em&gt; of geometric objects.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image.png"/&gt; &lt;br/&gt;
Solution: &lt;strong&gt;BST&lt;/strong&gt; &lt;/p&gt;
&lt;h2 id="1d-range-search"&gt;1d range search&lt;/h2&gt;
&lt;p&gt;operations required:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;insert   &lt;/li&gt;
&lt;li&gt;search   &lt;/li&gt;
&lt;li&gt;delete   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;range search&lt;/em&gt;: all keys between k1 and k2   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;range count&lt;/em&gt;: how many keys are between k1 and k2   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ find points on an interval  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation-by-bst"&gt;implementation by BST&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;range count&lt;/strong&gt; &lt;br/&gt;
using the &lt;code&gt;rank …&lt;/code&gt;&lt;/p&gt;</summary><content type="html">&lt;h1 id="1-1d-range-search"&gt;1. 1d Range Search&lt;/h1&gt;
&lt;p&gt;Goal: &lt;em&gt;intersections&lt;/em&gt; of geometric objects.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image.png"/&gt; &lt;br/&gt;
Solution: &lt;strong&gt;BST&lt;/strong&gt; &lt;/p&gt;
&lt;h2 id="1d-range-search"&gt;1d range search&lt;/h2&gt;
&lt;p&gt;operations required:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;insert   &lt;/li&gt;
&lt;li&gt;search   &lt;/li&gt;
&lt;li&gt;delete   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;range search&lt;/em&gt;: all keys between k1 and k2   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;range count&lt;/em&gt;: how many keys are between k1 and k2   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ find points on an interval  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation-by-bst"&gt;implementation by BST&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;range count&lt;/strong&gt; &lt;br/&gt;
using the &lt;code&gt;rank()&lt;/code&gt; function for the BST (or use the size of a tree) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image002.png"/&gt; &lt;br/&gt;
注意什么时候要加1...   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;contains&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;range search&lt;/strong&gt; &lt;br/&gt;
类似inorder traversal的方式:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;find in left subtree (if could fall into range)   &lt;/li&gt;
&lt;li&gt;check current node   &lt;/li&gt;
&lt;li&gt;find in right subtree   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image003.png"/&gt; &lt;br/&gt;
running time: R+lgN (R=nb of nodes in range)   &lt;/p&gt;
&lt;h1 id="2-line-segment-intersection_1"&gt;2. Line Segment Intersection&lt;/h1&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;Orthognal line segment intersection search&lt;/em&gt;:  &lt;br/&gt;
find all intersections given N horizontal/vertical lines &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Non-degeneracy assumption: all x-coord and y-coord are distinct.    &lt;/p&gt;
&lt;p&gt;naive algo: check all pairs...   &lt;/p&gt;
&lt;h2 id="sweep-line-algorithm"&gt;Sweep-line algorithm&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image006.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;sweep a vertical line from left to right.    &lt;ul&gt;
&lt;li&gt;when hit the left end of horizontal-segment (h-seg) → insert into a BST   &lt;/li&gt;
&lt;li&gt;when hit the right end of a h-seg → delete from BST   &lt;/li&gt;
&lt;li&gt;when hit a vertical-seg: ⇒ 1d range search !    &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;关于怎么sweep的:&lt;/strong&gt; &lt;br/&gt;
没有仔细讲, 不过我觉得就是把所有的x坐标排好序, 有个&lt;a href="https://leetcode.com/problems/the-skyline-problem/"&gt;skyline问题&lt;/a&gt;也是涉及如何sweep的.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt; &lt;br/&gt;
running time is NlgN+R (R=nb of intersections).  &lt;br/&gt;
&lt;em&gt;proof.&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Sort by x-coord (or use PQ) → NlgN   &lt;/li&gt;
&lt;li&gt;insert/delete y-coord to BST → NlgN   &lt;/li&gt;
&lt;li&gt;range search → NlgN + R   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-kd-trees_1"&gt;3. Kd-trees&lt;/h1&gt;
&lt;p&gt;An extension of BST: &lt;em&gt;2d-keys&lt;/em&gt;.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;insert: insert 2d points   &lt;/li&gt;
&lt;li&gt;search   &lt;/li&gt;
&lt;li&gt;range search: &lt;em&gt;find all keys lying in a 2d rectangle (h-v rectangle)&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;range count   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="gird-implementation"&gt;gird implementation&lt;/h2&gt;
&lt;p&gt;divide space into a M-by-M grid (uniform squares). &lt;br/&gt;
space: N + M^2 &lt;br/&gt;
time: 1 + N/M^2  &lt;br/&gt;
→ choose square to balance space and time.  &lt;br/&gt;
problem: points are not uniformly distributed.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h2 id="2d-tree"&gt;2d tree&lt;/h2&gt;
&lt;p&gt;Use a tree to represent the subdivision of the space.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;2d tree&lt;/strong&gt;: recursively divide the space into 2 halfplanes &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;p&gt;construct the 2d tree by adding points: &lt;em&gt;alternating between horizontal and vertical partitioning for each level of tree&lt;/em&gt;.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;p&gt;Data structure: BST alternating x and y-coords as key.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h2 id="range-search-for-2d-tree"&gt;Range search for 2d tree&lt;/h2&gt;
&lt;p&gt;find all points lying in a rectangle.  &lt;br/&gt;
依然类似tree traversal算法:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;check point in node   &lt;/li&gt;
&lt;li&gt;find in left subtree (if could be in range — the rectangle &lt;em&gt;intersects&lt;/em&gt; the splitting line)   &lt;/li&gt;
&lt;li&gt;find in right subtree   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;analysis&lt;/strong&gt; &lt;br/&gt;
Typical case: R + lgN &lt;br/&gt;
worst case: R+ sqrt(N) (even if tree is balanced) &lt;br/&gt;
(proof is hard)   &lt;/p&gt;
&lt;h2 id="nearest-neighbour-seach"&gt;Nearest Neighbour seach&lt;/h2&gt;
&lt;p&gt;find closest point to a query point.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;check dist from query point to node   &lt;/li&gt;
&lt;li&gt;check in left tree (&lt;em&gt;if could contain a closer point — 和两点连线与splitting line的角度有关系&lt;/em&gt;)   &lt;/li&gt;
&lt;li&gt;check in right tree   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;analysis&lt;/strong&gt; &lt;br/&gt;
typical case: lgN &lt;br/&gt;
worst case: N   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Flocking boids&lt;/strong&gt; &lt;br/&gt;
3 simple rules to get a simulation of flocking.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;h2 id="kd-tree"&gt;Kd tree&lt;/h2&gt;
&lt;p&gt;partition the k-dim space into 2 halfspaces.  &lt;br/&gt;
cycle through k dimensions. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image014.png"/&gt; &lt;br/&gt;
(居然时一个本科生发现的!)   &lt;/p&gt;
&lt;p&gt;Nbody simulation: &lt;br/&gt;
treat clusters as an aggregated node   &lt;/p&gt;
&lt;h1 id="4-interval-search-tree_1"&gt;4. Interval search tree&lt;/h1&gt;
&lt;p&gt;1d interval search:　data are intervals   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;insert interval    &lt;/li&gt;
&lt;li&gt;search interval   &lt;/li&gt;
&lt;li&gt;delete interval   &lt;/li&gt;
&lt;li&gt;intersection query: find all intervals that intersects (lo,hi)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image015.png"/&gt; &lt;br/&gt;
Nondegeneracy assumption: all left endpoint of intervals are distinct.    &lt;/p&gt;
&lt;p&gt;API:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;put(Key lo, Key hi, Value val)   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;get(Key lo, Key hi)   &lt;/span&gt;
&lt;span class="code-line"&gt;delete(Key lo, Key hi)   &lt;/span&gt;
&lt;span class="code-line"&gt;Iterable&amp;lt;Key&amp;gt; intersects(Key lo, Key hi)&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="interval-search-tree"&gt;Interval search tree:&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;BST using left endpoint as key   &lt;/li&gt;
&lt;li&gt;in each node: store the &lt;em&gt;max right endpoint of the subtree&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;insert&lt;/strong&gt; &lt;br/&gt;
类似BST, 加上维护一下maxendpoint即可.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;search&lt;/strong&gt; &lt;br/&gt;
search &lt;em&gt;any one&lt;/em&gt; interval that intersects (lo,hi)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if node intersects, return   &lt;/li&gt;
&lt;li&gt;if left.maxendpoint &amp;lt; lo: go right   &lt;/li&gt;
&lt;li&gt;else: go left   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;*proof. * &lt;br/&gt;
主要证明一点: if no intersection to left ⇒ then no intersection to the right &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;h1 id="5-rectangle-intersection_1"&gt;5. Rectangle intersection&lt;/h1&gt;
&lt;p&gt;Goal:  find all intersection among N rectangles.  &lt;br/&gt;
(non degeneracy assumption: all x and y are distinct)    &lt;/p&gt;
&lt;p&gt;bottom line: linearithmic algo.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;sweep-line algorithm:&lt;/strong&gt; &lt;br/&gt;
sweep vertical line from left to right.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;when hit left part of a rect ⇒ put into an interval search tree   &lt;/li&gt;
&lt;li&gt;when hit right part of a rect ⇒ remove interval   &lt;/li&gt;
&lt;li&gt;every time befor adding ⇒ check intersection   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;reduces the 2d rect intersection pb to 1d interval search pb.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;complexity:  &lt;br/&gt;
NlgN+RlgN   &lt;/p&gt;
&lt;p&gt;summery:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_2/pasted_image019.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 5-1 Balanced Search Trees</title><link href="https://x-wei.github.io/notes/algoI_week5_1.html" rel="alternate"/><published>2015-08-26T16:00:00+02:00</published><updated>2015-08-26T16:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-26:/notes/algoI_week5_1.html</id><summary type="html">&lt;p&gt;goal: lgN for insert/search/delete operations (not necessarily &lt;em&gt;binary&lt;/em&gt; trees..) &lt;br/&gt;
3 algo: 2-3 tree, (left leaning) red-black tree, B-tree   &lt;/p&gt;
&lt;h1 id="1-2-3-search-trees"&gt;1. 2-3 Search Trees&lt;/h1&gt;
&lt;p&gt;def. &lt;strong&gt;2-3 tree&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;allow 1 or 2 keys per node, &amp;amp; 2 or 3 children per node:    &lt;ul&gt;
&lt;li&gt;2-node: one key, 2 children (ordinary BST node)   &lt;/li&gt;
&lt;li&gt;3-node: 2 …&lt;/li&gt;&lt;/ul&gt;&lt;/li&gt;&lt;/ul&gt;</summary><content type="html">&lt;p&gt;goal: lgN for insert/search/delete operations (not necessarily &lt;em&gt;binary&lt;/em&gt; trees..) &lt;br/&gt;
3 algo: 2-3 tree, (left leaning) red-black tree, B-tree   &lt;/p&gt;
&lt;h1 id="1-2-3-search-trees"&gt;1. 2-3 Search Trees&lt;/h1&gt;
&lt;p&gt;def. &lt;strong&gt;2-3 tree&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;allow 1 or 2 keys per node, &amp;amp; 2 or 3 children per node:    &lt;ul&gt;
&lt;li&gt;2-node: one key, 2 children (ordinary BST node)   &lt;/li&gt;
&lt;li&gt;3-node: 2 keys, 3 children (3 children: &lt;em&gt;less, between, more&lt;/em&gt;)   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;perfect balance&lt;/strong&gt;: every path from root to null link has the same length (2-3 tree的一个超好的性质, &lt;em&gt;类似于一个满二叉树&lt;/em&gt;!)   &lt;/li&gt;
&lt;li&gt;symmetric order: inorder traversal gives ascending order (和BST类似)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image.png"/&gt; &lt;br/&gt;
&lt;strong&gt;search&lt;/strong&gt; &lt;br/&gt;
Just follow the correct link... Natural generalization of search in BST...    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;insert&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;case 1: insert into a 2-node at bottom   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;just convert a 2-node into a 3-node   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;case 2: insert into a 3-node at bottom   &lt;ul&gt;
&lt;li&gt;create a temporary 4-node (three keys)   &lt;/li&gt;
&lt;li&gt;move middle key in 4-node into parent, split the rest two keys into two 2-nodes   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image001.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image002.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if parent becom a 3-node → continue the process   &lt;/li&gt;
&lt;li&gt;if arrived at the root (root is a 4-node with three keys): split it into three 2-nodes   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image004.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;splitting a 4-node&lt;/strong&gt;: can be done in constant time (&lt;em&gt;local transformation&lt;/em&gt;).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;h2 id="analysis"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;Invariant: maintains symmetric order and perfect balance.  &lt;br/&gt;
&lt;em&gt;proof.&lt;/em&gt; &lt;br/&gt;
each transformation maintains the order and the balance, all possible transformations:  &lt;br/&gt;
这个图很好, 3-node的插入一共有三种情况: 自身是root/父亲是2-node/父亲是3-node &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;performance&lt;/strong&gt; &lt;br/&gt;
every path from root to null link has the same length.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;direct implementation is complicated:    &lt;/li&gt;
&lt;li&gt;bottom line: &lt;em&gt;Could do it, but there's a better way.&lt;/em&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="2-red-black-bst_1"&gt;2. Red-Black BST&lt;/h1&gt;
&lt;p&gt;LLRB tree: left-leaning red-black tree.    &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;BST representation of the 2-3 trees&lt;/em&gt; &lt;br/&gt;
&lt;strong&gt;use internal left-leaning links for 3 nodes&lt;/strong&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;红色link即为internal left leaning link (红黑树就是这么来的), 用红色link连接起来的组成一个(虚拟的)3-node 或4-node.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;3-node用一个red link表示:    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;4-node用两个red link表示:    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image030.png"/&gt; ⇒ &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image029.png"/&gt; or &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image027.png"/&gt; or &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image028.png"/&gt; &lt;/p&gt;
&lt;p&gt;example:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h2 id="properties"&gt;properties&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;no node has two red links (不可以一个节点连两个red link)   &lt;/li&gt;
&lt;li&gt;every path from path to null link has the same number of &lt;em&gt;black&lt;/em&gt; links (想象所有red link都变为horizontal)   &lt;/li&gt;
&lt;li&gt;all red links lean left   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;h2 id="representation"&gt;representation&lt;/h2&gt;
&lt;p&gt;Each node has only one link from parent  &lt;br/&gt;
⇒ add a boolean to encode color of links (the color of the link &lt;em&gt;from parent&lt;/em&gt;).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;color&lt;/span&gt;&lt;span class="c1"&gt;;//true means red     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;isRed&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;false&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;color&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;insert to parent 操作: 只需把color变为RED即表示该节点 被变成了和父节点一起的一个(虚拟)节点.    &lt;/p&gt;
&lt;h2 id="elementary-operations"&gt;elementary operations&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;left-rotation&lt;/strong&gt; &lt;br/&gt;
(def: &lt;em&gt;convert a right-learning red link to left.&lt;/em&gt; ) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image013.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image014.png"/&gt; &lt;br/&gt;
(symmetric ordering and perfect black balance are maintained)    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;rotateLeft&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;    &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;.&lt;span class="nv"&gt;color&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;.&lt;span class="nv"&gt;color&lt;/span&gt;&lt;span class="c1"&gt;;   // not = BLACK   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;h&lt;/span&gt;.&lt;span class="nv"&gt;color&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;RED&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;s&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;right-rotation&lt;/strong&gt; &lt;br/&gt;
(temporarily turn a left-leaning red link to right) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image015.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;code&gt;private Node rotateRight(Node h){...}&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;right rotation 是为了应对这种情况:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image024.png"/&gt; rotateRight(c) ⇒ &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image023.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;color-flip&lt;/strong&gt; &lt;br/&gt;
(split a 4-node, with three kyes — two red links) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image017.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;private void filpColor(Node h){   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    h.color = RED;   &lt;/span&gt;
&lt;span class="code-line"&gt;    h.left.color = BLACK;   &lt;/span&gt;
&lt;span class="code-line"&gt;    h.right.color = BLACK;   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="implementation_1"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Basic strategy&lt;/strong&gt; &lt;br/&gt;
Maintain &lt;em&gt;one-to-one correspondence&lt;/em&gt; with 2-3 tree by applying elementary operations.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;search&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;Exactly&lt;/em&gt; the same as elementary BST. ( ⇒ The same code for floor and ceiling)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;insert&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;Each insert will generate a red link&lt;/strong&gt; (then should rotate to make it legal)   &lt;/p&gt;
&lt;p&gt;插入的时候有两种可能:    &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;insert into a 2-node at the bottom   &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image025.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;standart BST insert   &lt;/li&gt;
&lt;li&gt;if have red right link: rotateLeft   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image021.png"/&gt; &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;insert into a 3-node    &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;有三种可能: insert into left/middle/right, right最简单, left捎复杂, middle最复杂, 见下图:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image026.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;standard BST insert and color nodes   &lt;/li&gt;
&lt;li&gt;if necessary, rotate to balance 4-node, 比如:    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image031.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;flip colors to pass red link to upper level   &lt;/li&gt;
&lt;li&gt;if necessary, rotate to make all links left-leaning    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;ex: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image032.png"/&gt; &lt;br/&gt;
ex2: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image033.png"/&gt; &lt;/p&gt;
&lt;p&gt;视频最后一段的demo太帅了! 叹为观止!!   &lt;/p&gt;
&lt;h2 id="code"&gt;Code&lt;/h2&gt;
&lt;p&gt;原来&lt;strong&gt;只有4种(其实是3种)情况要调整&lt;/strong&gt;:    &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;em&gt;left = black, right = red&lt;/em&gt; &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image034.png"/&gt;    ⇒ rotateLeft(a)   &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;em&gt;left =red, left.right = red [这个不会出现, 因为这对于下一层来说是case 1..]&lt;/em&gt; &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image039.png"/&gt;    ⇒ rotateLeft(e) ⇒ 变为case 3    &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;em&gt;left = red, left.left = red&lt;/em&gt; &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image035.png"/&gt;    ⇒ rotateRight(s) ⇒ 变为case 4   &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;em&gt;left = red. right = red&lt;/em&gt; &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image036.png"/&gt;        ⇒ flipColor(r)   &lt;/p&gt;
&lt;p&gt;几个状态之间的转化:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image038.png"/&gt; &lt;/p&gt;
&lt;p&gt;**只要三行代码即可处理LLRB tree !! 老爷子牛逼...... ** &lt;br/&gt;
(这个也是在2007年algo第四版的时候才刚刚弄出来的, 以前的代码要复杂)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nt"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;put&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nt"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;k&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;v&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;if(nd==null)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;Node(k,v,RED)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;k.compareTo(nd.key)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;if(cmp==0)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd.val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;v&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;这里不急着返回&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;--&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;same&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;trick&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;BSTs..&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;if(cmp&amp;lt;0)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd.left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;put(nd.left,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;k,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;v)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd.right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;put(nd.right,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;k,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;v)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;modifications&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;maintain&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;LLRB&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;tree&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;property&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nf"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;isRed&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="kc"&gt;right&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;!&lt;/span&gt;&lt;span class="nf"&gt;isRed&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="err"&gt;.&lt;/span&gt;&lt;span class="kc"&gt;left&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;rotateLeft&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="err"&gt;//case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;1&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;//if(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.left)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.left.right)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd.left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;rotateLeft(nd.left)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;--&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;never&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;happen...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;if(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.left)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.left.right)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;rotateRight(nd)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;3&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;if(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.left)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;isRed(nd.right)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;flipColor(nd)&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="err"&gt;//case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;4&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这三行代码越看越精妙......    &lt;/p&gt;
&lt;h2 id="analysis_1"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image041.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;worst case&lt;/strong&gt;: the left path is &lt;em&gt;alternating red and black&lt;/em&gt;. &lt;br/&gt;
⇒ longest path &amp;lt;= 2 * shortest path  (height&amp;lt;= 2lgN)   &lt;/p&gt;
&lt;p&gt;practical applications: height ~ 1.0 lgN   &lt;/p&gt;
&lt;p&gt;summery:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image042.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-b-trees_1"&gt;3. B-trees&lt;/h1&gt;
&lt;p&gt;setting: data access in file system.  &lt;br/&gt;
&lt;em&gt;Probe is much expensive than accessing data within a page.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;Goal: access data using a minimum number of probes.   &lt;/p&gt;
&lt;h2 id="b-tree"&gt;B-tree&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;def.&lt;/strong&gt; &lt;br/&gt;
external nodes: contain just keys, not links &lt;br/&gt;
internal nodes: contain key-link pairs   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;def. B-tree&lt;/strong&gt; &lt;br/&gt;
Generalize 2-3 trees by allowing up to M-1 keys per node:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;blockquote&gt;
&lt;p&gt;= 2 keys in root   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;blockquote&gt;
&lt;p&gt;= M/2 keys in other nodes   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;/li&gt;
&lt;li&gt;external nodes contain client keys   &lt;/li&gt;
&lt;li&gt;internal nodes contain copies of keys to guide search   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image043.png"/&gt; &lt;/p&gt;
&lt;h2 id="searching"&gt;Searching&lt;/h2&gt;
&lt;p&gt;similar to BST/2-3tree &lt;br/&gt;
ex. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image044.png"/&gt; &lt;/p&gt;
&lt;p&gt;(Choose M as large as possible so that M links fit into a page)   &lt;/p&gt;
&lt;h2 id="insertion"&gt;Insertion&lt;/h2&gt;
&lt;p&gt;similar to 2-3 tree &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image045.png"/&gt; &lt;/p&gt;
&lt;h2 id="analysis_2"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image046.png"/&gt; &lt;/p&gt;
&lt;h2 id="system-implementations"&gt;System implementations&lt;/h2&gt;
&lt;p&gt;system implementations of RBtree. &lt;br/&gt;
java:  &lt;br/&gt;
&lt;code&gt;java.util.TreeMap&lt;/code&gt;, &lt;code&gt;java.util.TreeSet&lt;/code&gt;.   &lt;/p&gt;
&lt;p&gt;八卦1: &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week5_1/pasted_image047.png"/&gt; &lt;/p&gt;
&lt;p&gt;八卦2: 
Sedgewick 的朋友, &lt;a href="https://fr.wikipedia.org/wiki/Philippe_Flajolet"&gt;Philippe Flajolet&lt;/a&gt;, 是一个X!    &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 4-2b Binary Search Trees</title><link href="https://x-wei.github.io/notes/algoI_week4_2b.html" rel="alternate"/><published>2015-08-26T00:00:00+02:00</published><updated>2015-08-26T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-26:/notes/algoI_week4_2b.html</id><summary type="html">&lt;p&gt;(BST是锻炼递归代码的好题目)   &lt;/p&gt;
&lt;h1 id="1-binary-search-trees"&gt;1. Binary Search Trees&lt;/h1&gt;
&lt;p&gt;def. &lt;strong&gt;BST&lt;/strong&gt; &lt;br/&gt;
A binary tree where each node has a key:  &lt;br/&gt;
for every node, the key is larger than &lt;em&gt;all nodes in left&lt;/em&gt; subtree, smaller than &lt;em&gt;all nodes in right&lt;/em&gt; subtree.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image.png"/&gt; &lt;br/&gt;
Fields: key, val, left, right   &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;An inner class of BST nodes:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;private class …&lt;/code&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;p&gt;(BST是锻炼递归代码的好题目)   &lt;/p&gt;
&lt;h1 id="1-binary-search-trees"&gt;1. Binary Search Trees&lt;/h1&gt;
&lt;p&gt;def. &lt;strong&gt;BST&lt;/strong&gt; &lt;br/&gt;
A binary tree where each node has a key:  &lt;br/&gt;
for every node, the key is larger than &lt;em&gt;all nodes in left&lt;/em&gt; subtree, smaller than &lt;em&gt;all nodes in right&lt;/em&gt; subtree.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image.png"/&gt; &lt;br/&gt;
Fields: key, val, left, right   &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;An inner class of BST nodes:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;private class Node{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    private Key key;   &lt;/span&gt;
&lt;span class="code-line"&gt;    private Value val;   &lt;/span&gt;
&lt;span class="code-line"&gt;    private Node left, right;   &lt;/span&gt;
&lt;span class="code-line"&gt;    public Node(Key k, Value v){...}   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;skeleton implementation of BST:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;BST&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Value&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;root&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;k&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;put&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;v&lt;/span&gt;&lt;span class="p"&gt;){}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;delete&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;k&lt;/span&gt;&lt;span class="p"&gt;){}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Iterable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;(){}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;search&lt;/strong&gt; &lt;br/&gt;
recursive version:  &lt;br/&gt;
(或者把这个函数写到Node类里面也可以. )   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="c1"&gt;; // search miss   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="c1"&gt;; // search hit   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;non-recursive version:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;insert&lt;/strong&gt; &lt;br/&gt;
recursive version:  &lt;br/&gt;
(注意这个recursive函数的返回值不是void! 这里是一个trick: 返回的是在分叉以前的那个节点)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;non-recursive version: &lt;br/&gt;
不如递归版本优美...   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;true&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="c1"&gt;; break;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; break;}   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; break;}   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;complexity: depth of the BST.    &lt;/p&gt;
&lt;p&gt;shape of BST: depends on how the keys come in (order of insertion).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image001.png"/&gt; &lt;br/&gt;
if keys come in &lt;em&gt;random&lt;/em&gt; order: could be pretty well balanced.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;BST and quick-sort partitionning&lt;/strong&gt; &lt;br/&gt;
&lt;em&gt;The root of BST is just the pivot in quick sort partitioning  * &lt;br/&gt;
if all keys are distinct ⇒ one-to-one correspondence between quick sort and BST.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image002.png"/&gt; &lt;br/&gt;
⇒ &lt;/em&gt;&lt;em&gt;proposition&lt;/em&gt;&lt;em&gt; &lt;br/&gt;
if all keys are distinct and come in randome order, the average number of compares for a search/insert is ~2lnN (or 1.39lgN).  &lt;br/&gt;
&lt;/em&gt;proof.* &lt;br/&gt;
证明见quicksort那里的数学推导...    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;proposition &lt;/strong&gt;(Reed, 2003) &lt;br/&gt;
N distinct keys come in random order, average tree height = 4.300lnN   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Worst-case:&lt;/strong&gt; &lt;br/&gt;
The tree becomes just like a linked list: ~N for insertion and search   &lt;/p&gt;
&lt;h1 id="2-oredered-operations-in-bst_1"&gt;2. Oredered Operations in BST&lt;/h1&gt;
&lt;p&gt;task: ordered opeartions   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;min()/max()&lt;/code&gt;: min/max key   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;deleteMin()/deleteMax()&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;&lt;code&gt;floor(Key k)/ceiling(Key k)&lt;/code&gt;: largest key &amp;lt;=k / smallest key &amp;gt;=k   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;rank(Key k)&lt;/code&gt;: nb of keys &amp;lt; key   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;select(int i)&lt;/code&gt;: key with rank=i   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;Iterator&amp;lt;Key&amp;gt; keys(lo, hi)&lt;/code&gt;: iterates through [lo, hi]   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="minmax"&gt;min/max&lt;/h2&gt;
&lt;p&gt;easy &lt;br/&gt;
min: left-most &lt;br/&gt;
max: right-most &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h2 id="floorceiling"&gt;floor/ceiling&lt;/h2&gt;
&lt;p&gt;a little more complexed...    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;floor (ceiling is similar)&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if k==nd.key   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;return nd.val   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if k&amp;lt;nd.key   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;the floor &lt;em&gt;must&lt;/em&gt; be in the left subtree   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if k&amp;gt;nd.key   &lt;ul&gt;
&lt;li&gt;如果min(nd.right) &amp;gt; k: 返回nd.val   &lt;/li&gt;
&lt;li&gt;如果min(nd.right) &amp;lt;= k: go to right   &lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;floor&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;largest&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;element&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="w"&gt;       &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;         &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="c1"&gt;;//case 1   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;floor&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//case 2   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;||&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;min&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="nv"&gt;case&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;val&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;floor&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;他提供的版本和我写的不一样: 递归函数floor返回的也是一个Node:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;h2 id="rankselect"&gt;rank/select&lt;/h2&gt;
&lt;p&gt;In each node, store the number of nodes in the subtree: &lt;em&gt;add an extra field&lt;/em&gt;.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;size&lt;/strong&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;...&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;// this is why we do not put size() inside the class Node!   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;.....&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="c1"&gt;;//maintain count for each node   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;rank&lt;/strong&gt; &lt;br/&gt;
(return nb of keys &amp;lt; k)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if nd.key==k   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;return size(nd.left)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if nd.key&amp;gt;k   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;return rank(nd.left, k)   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;if nd.key&amp;lt;k   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;return size(nd.left)+1+rank(nd,right, k)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;//remember null case   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nv"&gt;rank&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;,&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;select() similar...   &lt;/p&gt;
&lt;h2 id="iteration"&gt;iteration&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Inorder traversal 中序遍历&lt;/strong&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;keys&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;inorder&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;inorder&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Queue&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;inorder&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;q&lt;/span&gt;.&lt;span class="nv"&gt;enqueue&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;inorder&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;property&lt;/strong&gt; &lt;br/&gt;
inorder-traversal gives the keys &lt;em&gt;in ascending order&lt;/em&gt;.  &lt;br/&gt;
(proof by induction)   &lt;/p&gt;
&lt;h1 id="3-deletions-in-bst_1"&gt;3. Deletions in BST&lt;/h1&gt;
&lt;p&gt;one final function to implement: delete(Key k), deleteMin(), deleteMax() &lt;br/&gt;
→ and remember to update the count field...   &lt;/p&gt;
&lt;p&gt;(感觉这篇文章其实就讲的很清楚了: &lt;a href="http://www.algolist.net/Data_structures/Binary_search_tree/Removal"&gt;http://www.algolist.net/Data_structures/Binary_search_tree/Removal&lt;/a&gt;   这个在递归函数里使用了parent这个参数)   &lt;/p&gt;
&lt;h2 id="lazy-approch"&gt;lazy approch&lt;/h2&gt;
&lt;p&gt;&lt;code&gt;put(k, null)&lt;/code&gt;, and leave the key in the tree (tombstone) &lt;br/&gt;
→ not good if have large number of tombstons...    &lt;/p&gt;
&lt;h2 id="deleteminmax"&gt;deleteMin/Max&lt;/h2&gt;
&lt;p&gt;go the the left-most node → replace it with its right node.  &lt;br/&gt;
Recusive function with the &lt;em&gt;returning-node trick&lt;/em&gt;:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;deleteMin&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="c1"&gt;; // this might not happen   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;deleteMin&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//remember to maintain the count field   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这个递归的技巧又一次使用了.   &lt;/p&gt;
&lt;h2 id="hibbard-deletion"&gt;Hibbard deletion&lt;/h2&gt;
&lt;p&gt;first find node with the key to delete, 3 cases:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;0 children:    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;simply set parent link to null &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;1 child:    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;replace parent link with the child &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;2 children (most subtle)&lt;/strong&gt; &lt;ul&gt;
&lt;li&gt;first replace node key with smallest key in right subtree   &lt;/li&gt;
&lt;li&gt;remove the smallest key in right subtree   &lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;code of Hibbard deletion&lt;/strong&gt; &lt;br/&gt;
Again (for the 3rd time) use the &lt;em&gt;return-nd trick&lt;/em&gt;...   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="c1"&gt;;// search miss   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;.&lt;span class="nv"&gt;compareTo&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;,&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nv"&gt;null&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;min&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k2&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k2&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;left&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;.&lt;span class="nv"&gt;right&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;nd&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;root&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;感觉用了recursive return-nd 这个trick的实现很漂亮.... 比那篇博客里放一个参数进递归函数以及用auxroot的办法要好不少...    &lt;/p&gt;
&lt;h2 id="analysis_1"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;problem: &lt;em&gt;not symmetric&lt;/em&gt; &lt;br/&gt;
If random insert and delete for a while ⇒ tree become much less balanced ! Tree height tend to be sqrt(N).    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;summery&lt;/strong&gt; &lt;br/&gt;
BST is much better in average case, but not guaranteed for worst case.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2b/pasted_image009.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 4-2a Elementry Symbol Tables</title><link href="https://x-wei.github.io/notes/algoI_week4_2a.html" rel="alternate"/><published>2015-08-25T00:00:00+02:00</published><updated>2015-08-25T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-25:/notes/algoI_week4_2a.html</id><summary type="html">&lt;h1 id="1-symbol-table-api"&gt;1. Symbol Table API&lt;/h1&gt;
&lt;p&gt;key-value pair abstraction    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;insert&lt;/strong&gt; a value with a key   &lt;/li&gt;
&lt;li&gt;given a key, &lt;strong&gt;search&lt;/strong&gt; for its value   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="association-array-abstraction"&gt;Association array abstraction&lt;/h2&gt;
&lt;p&gt;Associate a value to a key — generalized array: &lt;em&gt;a[key]=val&lt;/em&gt;.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;ST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//remove key if value=null …&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;h1 id="1-symbol-table-api"&gt;1. Symbol Table API&lt;/h1&gt;
&lt;p&gt;key-value pair abstraction    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;insert&lt;/strong&gt; a value with a key   &lt;/li&gt;
&lt;li&gt;given a key, &lt;strong&gt;search&lt;/strong&gt; for its value   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="association-array-abstraction"&gt;Association array abstraction&lt;/h2&gt;
&lt;p&gt;Associate a value to a key — generalized array: &lt;em&gt;a[key]=val&lt;/em&gt;.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;ST&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;put&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;v&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//remove key if value=null   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;get&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;//return null if key is absent   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;delete&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;contains&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;isEmpty&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;size&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Iterable&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;keys&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;//better to return an ordered sequence of keys   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;conventions:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;values are not null   &lt;/li&gt;
&lt;li&gt;get() returns null if key not present   &lt;/li&gt;
&lt;li&gt;put() can &lt;em&gt;overwrite&lt;/em&gt; older value   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ some one-line implementations:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;contains: &lt;code&gt;return get(k)!=null;&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;delete: &lt;code&gt;put(k, null);&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Assume keys to be comparable: &lt;code&gt;class ST&amp;lt;Key implements Comparable&amp;lt;Key&amp;gt;, Value&amp;gt;&lt;/code&gt;— can thus use &lt;code&gt;compareTo()&lt;/code&gt; method.  &lt;br/&gt;
Else →  we can only use the &lt;code&gt;equals()&lt;/code&gt; method...  &lt;br/&gt;
Be careful when implementing the equals method: 坑不少...  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2a/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-elementary-implementations_1"&gt;2. Elementary implementations&lt;/h1&gt;
&lt;p&gt;naive implementations   &lt;/p&gt;
&lt;h2 id="using-unordered-linked-list"&gt;using unordered linked list&lt;/h2&gt;
&lt;p&gt;&lt;em&gt;ListNode{key, value, next}&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;search: scan through all keys ~N   &lt;/li&gt;
&lt;li&gt;insert: scan through, if not found, add to front ~N   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2a/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;h2 id="using-ordered-array"&gt;using ordered array&lt;/h2&gt;
&lt;p&gt;using 2 arrays: &lt;em&gt;keys[] (sorted), vals[]&lt;/em&gt; &lt;br/&gt;
⇒ can improve performance by binary search   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;search operation&lt;/strong&gt; &lt;br/&gt;
write a function rank() that returns the number of keys &amp;lt; k searched.  &lt;br/&gt;
找不到的时候: &lt;em&gt;比k小的元素个数=lo (lo&amp;gt;hi, 可以想想当hi=lo以后是怎么移动的)&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;rank&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;cmp&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;compareTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;cmp&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Using rank() to implement the get() method:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Value&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;rk&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;rank&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rk&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;keys&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;rk&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;compareTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vals&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;rk&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;insert operation&lt;/strong&gt; &lt;br/&gt;
Like insertion sort, time complexity is ~N for each insert.    &lt;/p&gt;
&lt;p&gt;summery:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2a/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-ordered-opeartions_1"&gt;3. Ordered Opeartions&lt;/h1&gt;
&lt;p&gt;When keys are comparable ⇒ provide &lt;em&gt;more functionalities&lt;/em&gt; in the API.  &lt;br/&gt;
for example:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;min()/max()&lt;/code&gt;: min/max key   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;deleteMin()/deleteMax()&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;&lt;code&gt;floor(Key k)/ceiling(Key k)&lt;/code&gt;: largest key &amp;lt;=k / smallest key &amp;gt;=k   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;rank(Key k)&lt;/code&gt;: nb of keys &amp;lt; key   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;select(int i)&lt;/code&gt;: key with rank=i   &lt;/li&gt;
&lt;li&gt;&lt;code&gt;Iterator&amp;lt;Key&amp;gt; keys(lo, hi)&lt;/code&gt;: iterates through [lo, hi]   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2a/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_2a/pasted_image003.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 4-1 Priority Queue</title><link href="https://x-wei.github.io/notes/algoI_week4_1.html" rel="alternate"/><published>2015-08-24T00:00:00+02:00</published><updated>2015-08-24T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-24:/notes/algoI_week4_1.html</id><summary type="html">&lt;h1 id="1-api-and-elementary-implementations"&gt;1. API and elementary implementations&lt;/h1&gt;
&lt;p&gt;Collection: data struct for inserting and deleting items (ex. stack and queue).  &lt;br/&gt;
Priority queue: a special kind of collection — remove &lt;em&gt;largest/smallest&lt;/em&gt; element.    &lt;/p&gt;
&lt;p&gt;API:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Max&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Kye&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;MaxPQ&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;delMax&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public …&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;h1 id="1-api-and-elementary-implementations"&gt;1. API and elementary implementations&lt;/h1&gt;
&lt;p&gt;Collection: data struct for inserting and deleting items (ex. stack and queue).  &lt;br/&gt;
Priority queue: a special kind of collection — remove &lt;em&gt;largest/smallest&lt;/em&gt; element.    &lt;/p&gt;
&lt;p&gt;API:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Max&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Kye&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;MaxPQ&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;insert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;k&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;delMax&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;max&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;size&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="pq-client-example"&gt;PQ client example&lt;/h2&gt;
&lt;p&gt;find &lt;em&gt;M largest&lt;/em&gt; elements from N items. (N is too huge to store) &lt;br/&gt;
⇒ 思路: 用 &lt;strong&gt;Min&lt;/strong&gt;&lt;em&gt;PQ&lt;/em&gt;, 当size&amp;gt;M时删掉最小元素 — 最后剩下的就是最大的M个元素了.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h2 id="elementarynaive-implementations"&gt;elementary(naive) implementations&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;unordered array implementation&lt;/strong&gt; &lt;br/&gt;
insert ~1,  &lt;br/&gt;
remove ~N   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;ordered array implementation&lt;/strong&gt; &lt;br/&gt;
insert ~N — ~ insertion sort, &lt;br/&gt;
remove ~1   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;goal&lt;/strong&gt;:  &lt;br/&gt;
insert O(lgN) &amp;amp; remove max O(lgN)   &lt;/p&gt;
&lt;h1 id="2-binary-heaps_1"&gt;2. Binary Heaps&lt;/h1&gt;
&lt;p&gt;binary heap: a special kind of &lt;em&gt;complete binary tree&lt;/em&gt;.    &lt;/p&gt;
&lt;p&gt;def. "&lt;strong&gt;complete binary tree"&lt;/strong&gt; &lt;br/&gt;
All level except the last level are full, all nodes in the last level are as far left as possible.   &lt;br/&gt;
完全二叉树大概长这个样子:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;p&gt;property: a complete binary tree with N items has height = lgN.    &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;binary heap&lt;/strong&gt; &lt;br/&gt;
Binary heap is a complete binary tree that satisfies: &lt;em&gt;each node &amp;gt;= any of its 2 children&lt;/em&gt; ("heap ordering").    &lt;/p&gt;
&lt;p&gt;property of binary heap:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;max element is root   &lt;/li&gt;
&lt;li&gt;height is lgN   &lt;/li&gt;
&lt;li&gt;&lt;em&gt;each node still makes a heap&lt;/em&gt; (use this property to construct heap from bottom up)   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="array-representation-of-binary-heap"&gt;Array representation of binary heap&lt;/h2&gt;
&lt;p&gt;Use an array &lt;code&gt;a[]&lt;/code&gt; to represent a complete binary tree: very easy to get children and parent.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;index starting from 1&lt;/strong&gt; (root = a[1], do not use a[0])    &lt;/li&gt;
&lt;li&gt;for node at index &lt;code&gt;i&lt;/code&gt;, its children are: &lt;code&gt;i*2&lt;/code&gt; and &lt;code&gt;i*2+1&lt;/code&gt; &lt;/li&gt;
&lt;li&gt;for node at index &lt;code&gt;i&lt;/code&gt; (i&amp;gt;1), its parent is: &lt;code&gt;i/2&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;简言之就是:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;内部成员变量:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;MaxPQ&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Key&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;a&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;siftup (swim)&lt;/strong&gt; &lt;br/&gt;
if a node is larger than its parent: &lt;em&gt;exchange with parent until heap ordering is restored.&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;swim&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k/2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;/=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;⇒ &lt;strong&gt;use siftup for inserting elements&lt;/strong&gt; &lt;br/&gt;
when inserting an element, first append it to the end of the array, then siftup the element to its right position.    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public void insert(Key k){    &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;a[N++]=x;   &lt;/span&gt;
&lt;span class="code-line"&gt;swim(N);   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;siftdown (sink)&lt;/strong&gt; &lt;br/&gt;
if a node is smaller than its children: &lt;em&gt;exchange it with the bigger child.&lt;/em&gt; 用公司高层变动来类比很形象...    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sink&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k*2&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="vm"&gt;?&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k*2+1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;maxIndex&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;⇒ use siftdown for deleting max operation&lt;/strong&gt; &lt;br/&gt;
First put a[N] to the position of root, then sink. (注意要防止loitering)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;delMax&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;Key&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ret&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;N--&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;avoid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;loitering&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sink&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ret&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;insert: ~lgN &lt;br/&gt;
remove max: ~lgN   &lt;/p&gt;
&lt;p&gt;improvements:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;use a &lt;strong&gt;d-way heap&lt;/strong&gt; instead of a 2-way heap (for ex. 3-way heap, the children of i are i&lt;em&gt;3, i&lt;/em&gt;3+1, i*3+2, the parent of i is i/3)   &lt;/li&gt;
&lt;li&gt;Fibonacci heap: insert is &lt;em&gt;~1&lt;/em&gt;, remove max still ~lgN, (but too complicated to use in practice).    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;p&gt;considerations:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;use immutable keys to avoid client from changing the keys (&lt;code&gt;final&lt;/code&gt; keyword in java)   &lt;/li&gt;
&lt;li&gt;underflow/overflow: throw exceptions for delMax() when empty, use resizing array for implementation.   &lt;/li&gt;
&lt;li&gt;expand the API with other operations: remove an arbitrary item, change the prority of an item (like handling an array)...   &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-heapsort_1"&gt;3. Heapsort&lt;/h1&gt;
&lt;p&gt;Basic idea:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;create a max heap with all N entries &lt;strong&gt;("heap-construction")&lt;/strong&gt; &lt;/li&gt;
&lt;li&gt;then repeatedly remove all N items &lt;strong&gt;("sortdown")&lt;/strong&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="implementation_1"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;heap construction&lt;/strong&gt; &lt;br/&gt;
Construct the heap using a &lt;strong&gt;bottom-up&lt;/strong&gt; method: build the heaps with small size first.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;one-node heaps (jus leaf node of heap): need not consider   &lt;/li&gt;
&lt;li&gt;larger heaps: children(subtrees) are already heap-order → just perform sink operation for root   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ &lt;em&gt;sink elements at indices from N/2 to 1&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="c1"&gt;; k&amp;gt;=1; k++)   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;sink&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;k&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;→ complexity is &lt;strong&gt;linear&lt;/strong&gt;, see analysis below.    &lt;/p&gt;
&lt;p&gt;&lt;em&gt;&lt;em&gt;heap destruction ** &lt;br/&gt;
now that we have a max-heap, to get the sorted array &lt;/em&gt;in-place,&lt;/em&gt; simply do:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;exch&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="mi"&gt;1&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;sink&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis_1"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt; &lt;br/&gt;
Heap construction uses &lt;strong&gt;&amp;lt;2N&lt;/strong&gt; compares and exchanges.  &lt;br/&gt;
&lt;em&gt;proof&lt;/em&gt; &lt;br/&gt;
一个有h层的heap, 高度为k的subtree有 2^(h-k)个, 每个subtree最多可以交换k次(从root交换到最底层)  &lt;br/&gt;
→ 每一层最多有 k*2^(h-k) 次交换  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image007.png"/&gt; &lt;br/&gt;
(第一个等式可以用数学归纳法证...)  &lt;br/&gt;
&lt;a href=""&gt;详细证明见http://algs4.cs.princeton.edu/24pq/&lt;/a&gt;  (Q20答案)   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt; &lt;br/&gt;
Heapsort use &amp;lt; 2NlgN compares and exchanges.    &lt;/p&gt;
&lt;p&gt;Heapsort is the first &lt;em&gt;in-place&lt;/em&gt; sorting algorithm with NlgN &lt;em&gt;worst-case&lt;/em&gt; performance.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ heapsort is &lt;em&gt;optimal for time and space&lt;/em&gt;, but:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;inner loop is longer than quicksort   &lt;/li&gt;
&lt;li&gt;poor use of cache memory (too many references to cache — look far away from the array entry when going down through the tree)   &lt;/li&gt;
&lt;li&gt;not stable: because it does long-distance exchanges   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Summary:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-event-driven-simulation_1"&gt;4. Event-driven simulation&lt;/h1&gt;
&lt;p&gt;Goal: simulating the motion of N particles in elastic collision (using a priority queue).  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h2 id="model"&gt;model&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image009.png"/&gt; &lt;br/&gt;
bouncing balls (without collision) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;p&gt;Ball class:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;p&gt;challenge: which objects to check? How to do it efficently ?   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Time driven simulation&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;upate the position of balls every &lt;code&gt;dt&lt;/code&gt; seconds   &lt;/li&gt;
&lt;li&gt;if overlap detected: figure how the velocity change and continue the simulation.    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;problem with time-driven simulation:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;1/2*N^2 overlap check per time unit   &lt;/li&gt;
&lt;li&gt;if dt small: too much calculation   &lt;/li&gt;
&lt;li&gt;if dt too large: might miss collisions   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="event-driven-simulation"&gt;Event driven simulation&lt;/h2&gt;
&lt;p&gt;change state only when something happens   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;particles move in straight line before collision   &lt;/li&gt;
&lt;li&gt;→ collision time can be &lt;em&gt;predicted&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;maintain PQ for collisions, key=collision time    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;collision prediction&lt;/strong&gt; &lt;br/&gt;
input: each particle has radius &lt;code&gt;s&lt;/code&gt;, position &lt;code&gt;(rx, ry)&lt;/code&gt;, velocity &lt;code&gt;(vx, vy)&lt;/code&gt;. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image013.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image014.png"/&gt; &lt;br/&gt;
(美国高中物理这么凶残?...)   &lt;/p&gt;
&lt;h2 id="implementation_2"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;anyway, 这个是封装好的类: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image015.png"/&gt; &lt;br/&gt;
注意, 使用了count记录一个particle到目前为止的碰撞次数.    &lt;/p&gt;
&lt;p&gt;initialization: &lt;strong&gt;quadratic&lt;/strong&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Fill PQ with all &lt;em&gt;potential&lt;/em&gt;  particle-particle collisions   &lt;/li&gt;
&lt;li&gt;Fill (the same) PQ with all &lt;em&gt;potential&lt;/em&gt;  particle-wall collisions   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;**Main loop **   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;get next event from PQ, event time = t   &lt;/li&gt;
&lt;li&gt;ignore if the event is &lt;em&gt;invalidated&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;advance all particles to time t   &lt;/li&gt;
&lt;li&gt;update velocities   &lt;/li&gt;
&lt;li&gt;predict future collisions and insert to PQ   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image018.png"/&gt; &lt;br/&gt;
判断invalidate:  &lt;br/&gt;
一个event构造(predict)时记录粒子构造时刻的碰撞次数(countA, countB), &lt;br/&gt;
然后在调用invalidate的时候, 如果粒子的碰撞次数发生了改变, 则返回false.  &lt;br/&gt;
(详见他们的代码: &lt;a href="http://algs4.cs.princeton.edu/61event/CollisionSystem.java.html"&gt;http://algs4.cs.princeton.edu/61event/CollisionSystem.java.html&lt;/a&gt;)   &lt;/p&gt;
&lt;p&gt;Event class:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image016.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week4_1/pasted_image017.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 3-2 Quicksort</title><link href="https://x-wei.github.io/notes/algoI_week3_2.html" rel="alternate"/><published>2015-08-22T00:00:00+02:00</published><updated>2015-08-22T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-22:/notes/algoI_week3_2.html</id><summary type="html">&lt;p&gt;(maybe best algorithm for sorting.)   &lt;/p&gt;
&lt;h1 id="1-quicksort"&gt;1. Quicksort&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;Idea:&lt;/strong&gt; &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;shuffle the array     &lt;/li&gt;
&lt;li&gt;&lt;em&gt;Partition&lt;/em&gt; the array into two subarrays to left and right of pivot  (&lt;em&gt;now pivot is &lt;/em&gt;&lt;strong&gt;in its final position&lt;/strong&gt;)   &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;no larger entry to the left of pivot   &lt;br/&gt;
no smaller entry to the right of pivot     &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;sort each subarray recursively …&lt;/li&gt;&lt;/ol&gt;</summary><content type="html">&lt;p&gt;(maybe best algorithm for sorting.)   &lt;/p&gt;
&lt;h1 id="1-quicksort"&gt;1. Quicksort&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;Idea:&lt;/strong&gt; &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;shuffle the array     &lt;/li&gt;
&lt;li&gt;&lt;em&gt;Partition&lt;/em&gt; the array into two subarrays to left and right of pivot  (&lt;em&gt;now pivot is &lt;/em&gt;&lt;strong&gt;in its final position&lt;/strong&gt;)   &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;no larger entry to the left of pivot   &lt;br/&gt;
no smaller entry to the right of pivot     &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;sort each subarray recursively     &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image.png"/&gt; &lt;/p&gt;
&lt;h2 id="implemetation"&gt;Implemetation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;The partition process:&lt;/strong&gt; &lt;br/&gt;
这个方法也比较巧妙.  &lt;br/&gt;
Use 2 pointers i and j (个人觉得用hi, lo, pivot更好...) :    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image001.png"/&gt; &lt;br/&gt;
→ a[i]&amp;gt;=a[lo], a[j]&amp;lt;&lt;strong&gt;=&lt;/strong&gt;a[lo] (注意是大于&lt;strong&gt;等于&lt;/strong&gt;/小于&lt;strong&gt;等于&lt;/strong&gt;)    &lt;br/&gt;
⇒ exchange i and j    &lt;br/&gt;
→ Scan until i and j cross (ie. j&amp;lt;=i)    &lt;br/&gt;
⇒ finally exchange lo with &lt;strong&gt;j&lt;/strong&gt; &lt;br/&gt;
函数的签名定义的好: 把lo到hi部分的数组分成两部分, 并返回分割点的index.   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&amp;gt;=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;--; //a[j]&amp;lt;=a[lo]   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;--);   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;exchange&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ow"&gt;in&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;its&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;final&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;position&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;这个函数其实并不好写对:     &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;test for cross pointers is not trival (ex. edge case: the pivot is the smallest/largest entry in the range)   &lt;/li&gt;
&lt;li&gt;i&amp;lt;=hi is necessary !    &lt;/li&gt;
&lt;li&gt;for keys equal to a[lo]: better to stop at them   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;invariance:    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;p&gt;**Quicksort:   ** &lt;br/&gt;
使用partition函数和辅助sort函数(recursive).  注意在整个流程开始以前先shuffle一下.     &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;sort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Comparable&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;pivot&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;partition&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;sort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="nv"&gt;lo&lt;/span&gt;,&lt;span class="nv"&gt;pivot&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;sort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="nv"&gt;pivot&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;,&lt;span class="nv"&gt;hi&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;sort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Comparable&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;StdRandom&lt;/span&gt;.&lt;span class="nv"&gt;shuffle&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;; // don't forget to shuffle the array   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;sort&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="mi"&gt;0&lt;/span&gt;,&lt;span class="nv"&gt;a&lt;/span&gt;.&lt;span class="nv"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;The randomness is preserved: the subarrays after partitionning is still randomly ordered.      &lt;/p&gt;
&lt;h2 id="analysis"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;Performance: ~40% faster than mergesort.      &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Best case&lt;/strong&gt; &lt;/p&gt;
&lt;h1 id="compares-nlgn_1"&gt;compares = NlgN&lt;/h1&gt;
&lt;p&gt;(each partition will divide the array in half)     &lt;/p&gt;
&lt;p&gt;**Worst case  **   &lt;/p&gt;
&lt;h1 id="compares-12n2"&gt;compares = 1/2*N^2&lt;/h1&gt;
&lt;p&gt;N+(N-1)+...+1 &lt;br/&gt;
if the array is already in order, &lt;em&gt;each partition will have one subarray of length=0&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;**Average case  **   &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;&lt;em&gt;proposition  ** &lt;br/&gt;
On average, for array with N distinct keys, the #compares =  ~2NlnN, #exchanges = ~1/2&lt;/em&gt;NlnN.    &lt;br/&gt;
&lt;/em&gt;Proof.*    &lt;br/&gt;
C(N) := # compares for N entries   &lt;br/&gt;
pivot 在N个数离的排名是uniform的    &lt;br/&gt;
接下来的数学推到很漂亮(不过可能没啥用..)     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image003.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image004.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image006.png"/&gt; &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;(上面最后一行写错了... 是2NlnN...orz)
random shuffle: probalistic guarantee against worst case.    &lt;/p&gt;
&lt;p&gt;&lt;em&gt;&lt;em&gt;Pitfalls    ** &lt;br/&gt;
implementations will get &lt;/em&gt;quadratic&lt;/em&gt; performance if array:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;is sorted or reverse sorted   &lt;/li&gt;
&lt;li&gt;has many duplicates (even if randomized)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;Staility  ** &lt;br/&gt;
Quicksort is &lt;/strong&gt;NOT** stable.   &lt;br/&gt;
partitionning can make long range exchanges   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h2 id="practical-improvements"&gt;Practical improvements&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;cutoff to insertion sort for &amp;lt;10 items    &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ ~20% improvement    &lt;br/&gt;
Or we can leave the small subarrays unsorted and sort them at last using insertion sort      &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;estimate median by sampling 3 items       &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image008.png"/&gt; &lt;br/&gt;
 → 10% improvement     &lt;/p&gt;
&lt;h1 id="2-selection_1"&gt;2. Selection&lt;/h1&gt;
&lt;p&gt;Goal: &lt;em&gt;given un array, find the kth largest item.&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Upper bound for this problem: NlgN (just sort the array)    &lt;/li&gt;
&lt;li&gt;for small k (ex k=1,2,3), the upper bound is N (one-pass/two-pass)     &lt;/li&gt;
&lt;li&gt;Lower bound is N: at least have to look at everything     &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="quick-select"&gt;Quick select&lt;/h2&gt;
&lt;p&gt;Algo proposed also by Hoare:      &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;partition the array into two arrays left of pivot and right of pivot.      &lt;/li&gt;
&lt;li&gt;if pivot==k: return      &lt;/li&gt;
&lt;li&gt;continue the partition for just one of the subarrays       &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;类似于二分查找的过程....  &lt;br/&gt;
注意这里&lt;strong&gt;是不用递归的&lt;/strong&gt;! 因为partition函数返回的直接就是pivot&lt;em&gt;在整个数组里的&lt;/em&gt;位置!    &lt;/p&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;privater&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;select&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;StdRandom&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;shuffle&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;partition&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;这里不太理解为什么会在hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;lo的时候直接返回a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis_1"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Proposition  ** &lt;br/&gt;
Quick selection takes &lt;/strong&gt;linear*&lt;em&gt; time on average.   &lt;br/&gt;
&lt;/em&gt;proof  * &lt;br/&gt;
intuitively, each partition will ct the subarray size in half:  &lt;br/&gt;
N+N/2+N/4+... = 2N   &lt;br/&gt;
formal analysis 略...   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;worst case&lt;/strong&gt;: quadratic (but very rare to happen)   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Theoretical results&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;h1 id="3-duplicate-keys_1"&gt;3. Duplicate keys&lt;/h1&gt;
&lt;p&gt;if array contains many duplicate keys.    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;huge array     &lt;/li&gt;
&lt;li&gt;small number of distinct keys     &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;**for mergesort  ** &lt;br/&gt;
insensitive... always ~NlgN compares.     &lt;/p&gt;
&lt;p&gt;&lt;em&gt;&lt;em&gt;for quicksort  ** &lt;br/&gt;
Will get &lt;/em&gt;quadratic&lt;/em&gt; time if not stop on equal keys. (found in 1990s)    &lt;br/&gt;
mistake: put all items equal to pivot *to just one side   * &lt;br/&gt;
→ N^2 compares if all keys are equal from lo to hi.  &lt;br/&gt;
correct: put all items equal to pivot in their final place.    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h2 id="3-way-partitionning"&gt;3-way partitionning&lt;/h2&gt;
&lt;p&gt;(by Dijkstra)   &lt;br/&gt;
partition the array into 3 parts:     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;p&gt;Dijkstra's 3-way partition algo:  &lt;br/&gt;
使用3个指针: lt指向中间部分的左边界, gt指向右边界;  i指针从左向右扫描, 算法很subtle:     &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;lt=lo, gt=hi, i=lo   &lt;/li&gt;
&lt;li&gt;if a[i]==v : i++   &lt;/li&gt;
&lt;li&gt;if a[i]&amp;lt;v: exch(i,lt), i++, lt++   &lt;/li&gt;
&lt;li&gt;if a[i]&amp;gt;v: exch(i,gt), gt--    &lt;/li&gt;
&lt;li&gt;repeat until i and gt cross (i&amp;gt;gt)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;&lt;em&gt;invariance&lt;/em&gt;&lt;/strong&gt;:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;[lo, lt)&lt;/code&gt; &lt;strong&gt;&lt;em&gt;all &amp;lt; v&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;[lt, i)&lt;/code&gt; &lt;strong&gt;&lt;em&gt;all == v&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;(gt, hi]&lt;/code&gt; &lt;strong&gt;&lt;em&gt;all &amp;gt;v&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation-3-way-quick-sort"&gt;Implementation: 3-way quick sort&lt;/h2&gt;
&lt;p&gt;不必再写partition函数, 直接在sort递归函数里面.     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image014.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;递归函数别忘了先写终止条件&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="p"&gt;;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;不能写&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="c1"&gt;--);   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lt&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;gt&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image015.png"/&gt; &lt;br/&gt;
当N个数有很多重复的时候, lower bound可以变小于NlgN:     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image016.png"/&gt; &lt;br/&gt;
And Sedgewick proved that the 3-wy partition is propotional to the lower bound....     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-system-sorts_1"&gt;4. System Sorts&lt;/h1&gt;
&lt;p&gt;Arrays.sort() in java:   &lt;/p&gt;
&lt;p&gt;&lt;code&gt;import java.util.Arrays;&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image018.png"/&gt; &lt;br/&gt;
quicksort for primitive arrays, mergesort for objects: java设计者认为如果用obj array表示空间不是问题...   &lt;/p&gt;
&lt;p&gt;Pb in java's system sort: killer input exsit (havn't shuffle)...    &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image020.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image021.png"/&gt; &lt;br/&gt;
总结一下学过的5/6种排序:     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_2/pasted_image022.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 3-1 Mergesort</title><link href="https://x-wei.github.io/notes/algoI_week3_1.html" rel="alternate"/><published>2015-08-21T00:00:00+02:00</published><updated>2015-08-21T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-21:/notes/algoI_week3_1.html</id><summary type="html">&lt;p&gt;Two classical sorting algorithms: mergesort, quicksort.    &lt;/p&gt;
&lt;h1 id="1-mergesort"&gt;1. Mergesort&lt;/h1&gt;
&lt;p&gt;Divide and conquer: top 10 algorithms of the 20th century, invented by von Neumann.     &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Idea&lt;/strong&gt;:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;divide array into 2 halves   &lt;/li&gt;
&lt;li&gt;recursively sort each half   &lt;/li&gt;
&lt;li&gt;merge two sorted halves   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Merge&lt;/strong&gt;:  &lt;br/&gt;
Goal: a[lo] to a[mid] and a[mid+1] to a …&lt;/p&gt;</summary><content type="html">&lt;p&gt;Two classical sorting algorithms: mergesort, quicksort.    &lt;/p&gt;
&lt;h1 id="1-mergesort"&gt;1. Mergesort&lt;/h1&gt;
&lt;p&gt;Divide and conquer: top 10 algorithms of the 20th century, invented by von Neumann.     &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Idea&lt;/strong&gt;:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;divide array into 2 halves   &lt;/li&gt;
&lt;li&gt;recursively sort each half   &lt;/li&gt;
&lt;li&gt;merge two sorted halves   &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="implementation"&gt;Implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Merge&lt;/strong&gt;:  &lt;br/&gt;
Goal: a[lo] to a[mid] and a[mid+1] to a[hi] are sorted ⇒ get a[lo] to a[hi] sorted.  &lt;br/&gt;
→&lt;em&gt;use an auxiliary array to copy data&lt;/em&gt;: using 3 indices i,j,k.     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;merge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;note: we use &lt;code&gt;if(less(aux[j],aux[i]))&lt;/code&gt;instead of&lt;code&gt;if(less(aux[j],aux[i]))&lt;/code&gt;, because less(a,b) == true iff a&amp;lt;b (strict), and we want to make mergesort &lt;strong&gt;stable&lt;/strong&gt;. See section (5) below.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Assertion&lt;/strong&gt; &lt;br/&gt;
We can also add &lt;em&gt;assertions&lt;/em&gt;: &lt;code&gt;assert isSorted(a, lo, mid); assert isSorted(a,mid+1, hi);&lt;/code&gt; &lt;br/&gt;
Enable/disable assertion at runtime:  &lt;br/&gt;
&lt;code&gt;java -ea MyProgram&lt;/code&gt; //enable assertion &lt;br/&gt;
&lt;code&gt;java -da MyProgram&lt;/code&gt; //disable assertion: &lt;strong&gt;default&lt;/strong&gt; &lt;br/&gt;
Best practice:  &lt;br/&gt;
use assertions to check interval invariants; &lt;br/&gt;
do NOT use assert for external argument checking !    &lt;/p&gt;
&lt;p&gt;**Mergesort   ** &lt;br/&gt;
为了mergesort需要写两个辅助函数: merge和sort(recursive):   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;MergeSort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;AbstractSort&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;=&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;merge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;merge&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;aux&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;hi&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;mid&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb nb-Type"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;as&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;before&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;有几点注意的:    &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;注意递归终止条件是&lt;code&gt;hi&amp;lt;=lo&lt;/code&gt;, 不是&lt;code&gt;==&lt;/code&gt;.    &lt;/li&gt;
&lt;li&gt;实现的代码不难, 但是定义好辅助函数的参数并不简单... 比如在merge里使用了mid作为参数.    &lt;/li&gt;
&lt;li&gt;aux的数组直接写在了函数参数里面, 好处是可以防止反复声明数组带来的开销.   &lt;/li&gt;
&lt;li&gt;发现他们写的时候mid都是写成: &lt;code&gt;mid = lo+(hi-lo)/2&lt;/code&gt;, &lt;a href="http://stackoverflow.com/questions/25571359/why-we-write-lohi-lo-2-in-binary-search"&gt;查了一下&lt;/a&gt;发现这样的原因是为了防止hi+lo整数溢出...嗯有道理.    &lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id="analysis"&gt;Analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition (time)&lt;/strong&gt; &lt;br/&gt;
Mergesort takes at most NlgN compares and 6NlgN array access.  &lt;br/&gt;
&lt;em&gt;Proof.&lt;/em&gt; &lt;br/&gt;
def: C(N)=#compares for N elements, A(N)=#array access for N elements, the recurrence eq:  &lt;br/&gt;
C(N) &amp;lt;= 2&lt;em&gt;C(N/2) + N; C(1) = 0  (最多N次比较: 每个a[]的数都由比较得到)    &lt;br/&gt;
A(N) &amp;lt;= 2&lt;/em&gt;A(N/2) + 6N; A(1) = 0 (~~这里不太理解为什么是6N, 怎么数都是4N或者5N啊?......~~2N复制到aux, 2N复制回去, 2N比较)    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image001.png"/&gt; &lt;br/&gt;
(上图蓝色的一列是extra cost)      &lt;br/&gt;
或者用递推公式, 发现D(N)/N的递推关系:     &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image002.png"/&gt; &lt;br/&gt;
或者用数学归纳法:    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Proposition(memory)&lt;/strong&gt; &lt;br/&gt;
Mergesort takes N extra memory. &lt;br/&gt;
⇒ mergesort is NOT &lt;em&gt;in-place&lt;/em&gt; sorting method.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;def&lt;/strong&gt;. &lt;em&gt;"in-place"&lt;/em&gt; &lt;br/&gt;
A sorting algo is in-place if it uses &amp;lt;C*lgN extra memory.  &lt;br/&gt;
ex. insertion sort, shellsort, selection sort...   &lt;/p&gt;
&lt;h2 id="practical-improvements"&gt;Practical improvements&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;use insertion sort for small arrays:     &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;cutoff to insertion sort for &amp;lt;7 items.    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image004.png"/&gt; &lt;br/&gt;
⇒ lead to 20% improvement!     &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;stop if alread sorted: *a[mid]&amp;lt;a[mid+1]!   *   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;switch the role of &lt;code&gt;a[]&lt;/code&gt; and &lt;code&gt;aux[]&lt;/code&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image006.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h1 id="2-bottom-up-mergesort_1"&gt;2. Bottom-up Mergesort&lt;/h1&gt;
&lt;p&gt;bottom-up version of mergesort &lt;em&gt;without recursion&lt;/em&gt;.  &lt;br/&gt;
Idea:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;pass and merge subarrays of size 1 in pairs      &lt;/li&gt;
&lt;li&gt;repeat for subarrays of size 2,4,8,....      &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;p&gt;看着上面那个图好写一点... 就是每次用更大的size来两两merge一遍数组   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public static void sort(Comparable[] a){   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    Comparable[] aux = new Comparable[a.length];   &lt;/span&gt;
&lt;span class="code-line"&gt;    for(int sz=1;sz&amp;lt;a.length;sz*=2){   &lt;/span&gt;
&lt;span class="code-line"&gt;        for(int i=0;i&amp;lt;a.length-sz;i+=sz*2)   &lt;/span&gt;
&lt;span class="code-line"&gt;            merge( a,aux,i,i+sz-1,Math.min(i+sz*2-1) );//&amp;lt;-注意mid和hi的计算方法   &lt;/span&gt;
&lt;span class="code-line"&gt;    }   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="3-sorting-complexity_1"&gt;3. Sorting Complexity&lt;/h1&gt;
&lt;p&gt;some items:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;computational model: allowed operations, (ex. &lt;em&gt;decision tree for compare based sorting&lt;/em&gt;).     &lt;/li&gt;
&lt;li&gt;cost model: operation counts.    &lt;/li&gt;
&lt;li&gt;upper bound: cost guarantee (ex. NlgN for mergesort). .    &lt;/li&gt;
&lt;li&gt;lower bound: limit on cost guarantee for all algorithms (no algorithm can do better).    &lt;/li&gt;
&lt;li&gt;Optimal algorithm: algo with best cost guarantee. (upper bound=lower bound)   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;证明lower bound 的方法很有意思:    &lt;/p&gt;
&lt;h2 id="lower-bound-for-sorting"&gt;lower bound for sorting&lt;/h2&gt;
&lt;p&gt;(binary) decision tree for the case of 3 distinct items:      &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;p&gt;each possible ordering is a leaf of the decision tree → there are N! possible orderings → tree height should be lg(N!) = NlgN (cf. &lt;a href="https://en.wikipedia.org/wiki/Stirling%27s_approximation"&gt;https://en.wikipedia.org/wiki/Stirling%27s_approximation&lt;/a&gt;)    &lt;br/&gt;
&lt;em&gt;&lt;em&gt;proposition.  ** &lt;br/&gt;
Any compare-based sorting algorithm must have at least lg(N!)~NlgN compares in the worst case. (for N distinct keys)        &lt;br/&gt;
&lt;/em&gt;proof.&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;binary tree of height h has at most 2^h leaves     &lt;/li&gt;
&lt;li&gt;N! possible orderings → at least N! leaves     &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image010.png"/&gt; &lt;br/&gt;
 So, lower bound for sorting = ~NlgN ⇒ &lt;em&gt;mergesort &lt;/em&gt;&lt;strong&gt;is&lt;/strong&gt;&lt;em&gt; an asymptotical optimal algorithm&lt;/em&gt;. (In terms of time complexity, the shortcoming of mergesort is always the extra space usage)   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image011.png"/&gt; &lt;br/&gt;
 但是并不是说NlgN是&lt;em&gt;所有&lt;/em&gt;排序问题的下界:   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image012.png"/&gt; &lt;/p&gt;
&lt;h1 id="4-comparators_1"&gt;4. Comparators&lt;/h1&gt;
&lt;p&gt;Java mechenism for comparing same data on different ways.    &lt;/p&gt;
&lt;h2 id="comparable-interface"&gt;Comparable interface&lt;/h2&gt;
&lt;p&gt;→Sorting using &lt;em&gt;natural order&lt;/em&gt; for a data type. &lt;br/&gt;
    public class Data implements Comparable&lt;date&gt;{ &lt;br/&gt;
    public int compareTo(Date that){ &lt;br/&gt;
    //...} &lt;br/&gt;
    }   &lt;/date&gt;&lt;/p&gt;
&lt;h2 id="comparator-interface"&gt;Comparator interface&lt;/h2&gt;
&lt;p&gt;→Sorting using  an &lt;em&gt;alternative order&lt;/em&gt;. (total order property is required...)   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public interface Comparator&amp;lt;Key&amp;gt;{   &lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    int compare(Key v, Key w);   &lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;Comparator can be passed as arguments in java system sort:   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image013.png"/&gt; &lt;/p&gt;
&lt;p&gt;**Using Comparators in our sorting algos   ** &lt;br/&gt;
Use another signature:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;change Comparable to Object   &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;add Comparator in arguments   &lt;/p&gt;
&lt;p&gt;public static void sort(Object[] a, Comparator comparator); &lt;br/&gt;
public static boolean less(Comparator c, Object v, Object w);    &lt;/p&gt;
&lt;p&gt;public static void exch(Object[] a, int i, int j);   &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;**Implementing a comparator    ** &lt;br/&gt;
Add static comparator to a class:    &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;In the declaration of a class, define an inner class that implements the Comparator interface,    &lt;/li&gt;
&lt;li&gt;Then declare an instance of this inner class as a static final variable...   &lt;/li&gt;
&lt;li&gt;note: the inner class should be &lt;strong&gt;static&lt;/strong&gt; also.      &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image014.png"/&gt; &lt;br/&gt;
以上的方法目的是为某个类提供预先定义好的comparator(比如&lt;code&gt;String.CASE_INSENSITIVE_ORDER&lt;/code&gt;), 另外也可以直接再声明一个类作为comparator, 然后实例化这个类传进去, 就像之前做过的那样.    &lt;/p&gt;
&lt;p&gt;*&lt;em&gt;Application: Graham scan algo for convex hull  ** &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image015.png"/&gt; &lt;br/&gt;
We can get the result of compare by calling &lt;code&gt;ccw(a,b,c)&lt;/code&gt; : &lt;br/&gt;
&lt;/em&gt;ccw(p,q1,q2)=true ⇔ q2&amp;gt;q1 in terms of polar angle wrt p. (别忘了p是y坐标最小的点, 否则还要讨论角坐标为负数的情况, 见下图).    * &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image016.png"/&gt; &lt;/p&gt;
&lt;h1 id="5-stability_1"&gt;5. Stability&lt;/h1&gt;
&lt;p&gt;Typical application: first sort by student name then by section.    &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;def. :stable"&lt;/strong&gt; &lt;br/&gt;
&lt;em&gt;A stable sort preserves the relative order for items with equal keys.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;em&gt;Insertion sort and mergesort are stable, whereas selection sort and shell sort are not.&lt;/em&gt; (And always need to carefully check code: "less than" vs. "less than or equal to").   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;insertion sort:&lt;/strong&gt; &lt;br/&gt;
stable &lt;br/&gt;
proof: we never move equal items pass each other: &lt;code&gt;if(less(a[j], a[j-1])) exch(...)&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;**selection sort:  ** &lt;br/&gt;
not stable   &lt;br/&gt;
counter example:  &lt;br/&gt;
when exchanging A1 and B1, we move B1 behind B2    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;p&gt;**shell sort:  ** &lt;br/&gt;
counter example: long-dist exchanges   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week3_1/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;p&gt;**merge sort:   ** &lt;br/&gt;
stable &lt;br/&gt;
proof: suffices to verify that merge operation is stable, if keys are equal, always take element from left subarray.    &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 2-2 Elementary Sorts</title><link href="https://x-wei.github.io/notes/algoI_week2_2.html" rel="alternate"/><published>2015-08-18T00:00:00+02:00</published><updated>2015-08-18T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-08-18:/notes/algoI_week2_2.html</id><summary type="html">&lt;h1 id="1-introduction"&gt;1. Introduction&lt;/h1&gt;
&lt;p&gt;rearanging array of size N into ascending order &lt;br/&gt;
test client code: &lt;code&gt;Insertion.sort(a);&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;sort &lt;em&gt;any&lt;/em&gt; datatype &lt;/p&gt;
&lt;h3 id="callback"&gt;callback&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;callback = reference to executable code&lt;/em&gt; &lt;br/&gt;
i.e. passing functions as argument to sort() method&lt;br/&gt;
sort() function calls object's &lt;code&gt;compareTo()&lt;/code&gt; method  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image.png"/&gt; &lt;br/&gt;
→ implement the &lt;code&gt;Comparable&lt;/code&gt; interface:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;XX&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;XX …&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;h1 id="1-introduction"&gt;1. Introduction&lt;/h1&gt;
&lt;p&gt;rearanging array of size N into ascending order &lt;br/&gt;
test client code: &lt;code&gt;Insertion.sort(a);&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;sort &lt;em&gt;any&lt;/em&gt; datatype &lt;/p&gt;
&lt;h3 id="callback"&gt;callback&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;callback = reference to executable code&lt;/em&gt; &lt;br/&gt;
i.e. passing functions as argument to sort() method&lt;br/&gt;
sort() function calls object's &lt;code&gt;compareTo()&lt;/code&gt; method  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image.png"/&gt; &lt;br/&gt;
→ implement the &lt;code&gt;Comparable&lt;/code&gt; interface:    &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;XX&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Comparable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;XX&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;the interface: &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;    public interface Comparable&amp;lt;Item&amp;gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;        public int compareTo(Item that);&lt;/span&gt;
&lt;span class="code-line"&gt;    }&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;compareTo():&lt;br/&gt;
return -1 (if this&amp;lt;that)/+1/0; 
needs a &lt;em&gt;total order.&lt;/em&gt; 
→ in the sort() implementation:&lt;br/&gt;
has not dependencies on type of data.  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;compareTo&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="helper-functions"&gt;helper functions&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;less&lt;/p&gt;
&lt;p&gt;private static boolean less(Comparable v, Comparable u){
returnv.compareTo(u)&amp;lt;0;
}&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;exch&lt;/p&gt;
&lt;p&gt;private void exch(Comparable[] a, int i, int j) {
        Comparable swap = a[i];
        a[i] = a[j];
        a[j] = swap;
    }&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;isSorted&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;test if sorted
if algo passes the test using only less ant swap, then it's correct. &lt;/p&gt;
&lt;h1 id="2-selection-sort_1"&gt;2. Selection Sort&lt;/h1&gt;
&lt;p&gt;Idea: each time&lt;em&gt;: find the minimum from the remaining items.&lt;/em&gt;
&lt;strong&gt;a[min] is the smallest element to right of a[i] ⇒ swap a[i] and a[min]&lt;/strong&gt; (elements to left of i are sorted) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h2 id="invariants"&gt;invariants&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;entries to the left of i are in sorted order, and are fixed (&lt;em&gt;in final position&lt;/em&gt;) ever since&lt;/li&gt;
&lt;li&gt;no entry to the right of i is smaller than any entry to the left of i&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="implementation"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;SelectionSort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;AbstractSorting&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;min&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nf"&gt;min&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis"&gt;analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition:&lt;/strong&gt;
selection sort uses &lt;em&gt;N-1 + N-2 + ... + 1 = ~N^2/2&lt;/em&gt; compares, and &lt;em&gt;N&lt;/em&gt; exchanges. 
→ quadratic time&lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image003.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;insensitive&lt;/strong&gt; to input: quadratic time &lt;em&gt;even if input is already sorted.&lt;/em&gt; &lt;/li&gt;
&lt;li&gt;data movement is &lt;em&gt;minimum&lt;/em&gt;: linear time of exchanges (every exchange puts an item to its final position)&lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="3-insertion-sort_1"&gt;3. Insertion sort&lt;/h1&gt;
&lt;p&gt;quite different performance characteritics than selection sort. &lt;/p&gt;
&lt;p&gt;Idea: &lt;strong&gt;In iteration i: move all entries larger than a[i] to its left.&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;h2 id="invariants_1"&gt;invariants&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;entries to the left of i are in ascending order (but &lt;em&gt;not&lt;/em&gt; in final position)&lt;/li&gt;
&lt;li&gt;entries to the right of i are not yet been seen   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image005.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation_1"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;publc&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;InsertionSorting&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;AbstractSorting&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="c1"&gt;--){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j-1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2 id="analysis_1"&gt;analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition &lt;/strong&gt;(average case): &lt;br/&gt;
(the performance &lt;em&gt;on average&lt;/em&gt; — &lt;em&gt;for randomly sorted array&lt;/em&gt; ) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image007.png"/&gt; &lt;br/&gt;
&lt;em&gt;proof:&lt;/em&gt;
&lt;em&gt;expect each entry to move halfway back&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image008.png"/&gt; &lt;/p&gt;
&lt;h3 id="best-case-and-worst-case"&gt;best case and worst case&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;best case&lt;/strong&gt;
if array already sorted min ascending order: 
&lt;em&gt;N-1 compares, 0 exchanges.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;worst case&lt;/strong&gt;
if array sorted in descending order: 
every element goes all the way back → 1/2&lt;em&gt;N^2 compares,  1/2&lt;/em&gt;N^2 exchanges&lt;/p&gt;
&lt;h3 id="partially-sorted-arrays"&gt;partially  sorted arrays&lt;/h3&gt;
&lt;p&gt;def.&lt;strong&gt;" inversion"&lt;/strong&gt;
an inversion is a pair of entries that are out of order. &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;"partially sorted"&lt;/strong&gt;&lt;br/&gt;
An array is called partially sorted if the &lt;em&gt;number of inversions is &amp;lt;= c&lt;/em&gt;N. *&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;proposition. &lt;/strong&gt;&lt;br/&gt;
&lt;strong&gt;Insertion sort runs in linear time for partially sorted array.&lt;/strong&gt;
&lt;em&gt;proof.&lt;/em&gt;
&lt;em&gt;number of exchanges = number of inversions. *
&lt;/em&gt;number of compares = number of exchanges + N-1*&lt;/p&gt;
&lt;h1 id="4-shell-sort_2"&gt;4. Shell Sort&lt;/h1&gt;
&lt;p&gt;First non-trival sorting methode: an improvement of insertion sort. &lt;/p&gt;
&lt;p&gt;def. &lt;strong&gt;"h-sorted array"&lt;/strong&gt;&lt;br/&gt;
an array is h-sorted if every h-interleaved subarray is sorted. (h=1: just a sorted array)  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;p&gt;Idea: move entries &amp;gt;1 position at a time by &lt;em&gt;h-sorting&lt;/em&gt; the array, then decrease h.   &lt;/p&gt;
&lt;p&gt;use decreasing sequences of value h:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image010.png"/&gt; &lt;/p&gt;
&lt;h2 id="implementation_2"&gt;implementation&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;How to h -sort  &lt;/strong&gt;&lt;br/&gt;
simply insertion sort with &lt;em&gt;stride length=h&lt;/em&gt;.&lt;br/&gt;
why insertion sort: &lt;br/&gt;
for big h: small subarray &lt;br/&gt;
for small h: nearly in order   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt;&lt;br/&gt;
A g-sorted array &lt;em&gt;remains g-sorted&lt;/em&gt; after h-sorting it.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image011.png"/&gt; &lt;br/&gt;
(subtle to prove...)  &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;which sequence of h to use&lt;/strong&gt;
&lt;code&gt;3x+1&lt;/code&gt; sequence proposed by Knuth. &lt;em&gt;1,4,13,40....&lt;/em&gt;&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ShellSort&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;extends&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;AbstractSort&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;find&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;beginning&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;performs&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;sort&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+=&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;-=&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j-h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                        &lt;/span&gt;&lt;span class="n"&gt;exch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                    &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;isHsorted&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Comparable&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;h&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;less&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i-h&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;false&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;每次hsort, 外围的循环是&lt;code&gt;for(int i= h;i&amp;lt;N;i+=h)&lt;/code&gt;, 需要理解一下: i移动一次以后, 进行的是另一个subarray 的插入排序, 当移动到N-1的时候所有subarray的插入排序才结束. (也就是说不是先完成一个subarray的插入排序再完成另一个, 这些是插入排序是同步进行的)&lt;/p&gt;
&lt;h2 id="analysis_2"&gt;analysis&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;proposition (for worst case   )&lt;/strong&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image012.png"/&gt; &lt;br/&gt;
→ better than quadratic time !     &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;property  (found in practice)&lt;/strong&gt;&lt;/p&gt;
&lt;h1 id="of-compares-cte-n-of-h-used_1"&gt;of compares &amp;lt; Cte * N * (# of &lt;em&gt;h&lt;/em&gt; used )&lt;/h1&gt;
&lt;p&gt;→ #compares &amp;lt; NlgN * Cte &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image013.png"/&gt; &lt;br/&gt;
*accurate model has not been discovered  *&lt;/p&gt;
&lt;p&gt;(所以shellsort在实际使用中几乎和快速排序一样快! — 尽管没有数学证明来保证)&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;why we are interested in shell sort&lt;/strong&gt;
useful in practice: &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;fast for medium sized arrays (beat even the classical sophistiated algorithms)  &lt;/li&gt;
&lt;li&gt;tiny code volumn (used in embeded systems)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;lead to interesting questions for 50 years: &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;asymptotic growth rate ?&lt;/li&gt;
&lt;li&gt;best sequence of h ?&lt;/li&gt;
&lt;li&gt;average case performance ?&lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="5-shuffling"&gt;5. shuffling&lt;/h1&gt;
&lt;h2 id="shuffle-array-using-sort"&gt;shuffle array using sort&lt;/h2&gt;
&lt;p&gt;one way to shuffle an array: &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;for each array entry, generate a random real number&lt;/li&gt;
&lt;li&gt;sort the array of real numbers&lt;/li&gt;
&lt;li&gt;⇒ the original array is shuffled !&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;strong&gt;proposition  &lt;/strong&gt;&lt;br/&gt;
this shuffle sort produces a uniformly random permutation of input array &lt;br/&gt;
&lt;em&gt;drawback:  cost for sorting...&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Goal: get uniformly random permutation in &lt;em&gt;linear time&lt;/em&gt;.   &lt;/p&gt;
&lt;h2 id="knuth-shuffle"&gt;Knuth shuffle&lt;/h2&gt;
&lt;p&gt;algo:  &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;for i = [0,N):&lt;br/&gt;
    - r = rand( [0~i&lt;strong&gt;]&lt;/strong&gt; ) or rand( &lt;strong&gt;[&lt;/strong&gt;i, N-1] ) &lt;br/&gt;
    - swap a[r] and a[i]   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image014.png"/&gt;&lt;/p&gt;
&lt;p&gt;implementation: &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;shuffle&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;Object&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="c1"&gt;;i&amp;lt;a.length;i++){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;StdRandom&lt;/span&gt;.&lt;span class="nv"&gt;uniform&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nv"&gt;exch&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;a&lt;/span&gt;,&lt;span class="nv"&gt;r&lt;/span&gt;,&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;}&lt;span class="w"&gt;   &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;proposition&lt;/strong&gt;&lt;br/&gt;
Knuth algo produces an uniformly random permutation of input array. &lt;/p&gt;
&lt;p&gt;&lt;em&gt;proof.&lt;/em&gt;&lt;br/&gt;
Sufficient to prove that, for card i and position j, the proba(card i comes to position j) = 1/N. &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;if i&amp;lt;=j, P = 1/j * j/(j+1) * (j+1)/(j+2) * ... * (N-1)/N&lt;/li&gt;
&lt;li&gt;if j&amp;lt;i, P = 1/i * i/(i+1) * (i+1)/(i+2) * ... * (N-1)/N&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;CQFD.&lt;/p&gt;
&lt;h2 id="example-online-poker"&gt;example: online poker&lt;/h2&gt;
&lt;p&gt;&lt;a href="https://www.cigital.com/papers/download/developer_gambling.php"&gt;https://www.cigital.com/papers/download/developer_gambling.php&lt;/a&gt;  ←那个扑克网站已经被黑出翔了...  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image015.png"/&gt; &lt;br/&gt;
bugs: &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;r never get 52 (52th card never moved)&lt;/li&gt;
&lt;li&gt;r = rand(N) instead of rand(0~i), → shuffle not uniform&lt;/li&gt;
&lt;li&gt;random() uses 32bit seed: only 2^32 possible shuffles, &lt;em&gt;2^32&amp;lt;52!&lt;/em&gt;&lt;/li&gt;
&lt;li&gt;seed = millisec from midnight, ~86*10^6 suffles&lt;/li&gt;
&lt;/ol&gt;
&lt;h1 id="6-convex-hull_1"&gt;6. Convex Hull&lt;/h1&gt;
&lt;p&gt;application of sorting for the field of computational geometry.  &lt;/p&gt;
&lt;h2 id="convex-hull"&gt;convex hull&lt;/h2&gt;
&lt;p&gt;smallest polygoneenclosing all N points. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image017.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;input: N points&lt;/li&gt;
&lt;li&gt;output: sequence of &lt;em&gt;vertices&lt;/em&gt; in counterclockwise (&lt;em&gt;ccw&lt;/em&gt;) order. &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;application: robot motion planning; farest pair.   &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;geometric properties&lt;/strong&gt;:   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;can traverse convex hull by making only ccw turns&lt;/li&gt;
&lt;li&gt;let p be the point with lowest y-coord, wrt p, vertices appear in increasing order of polar angle.   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image018.png"/&gt; &lt;/p&gt;
&lt;h2 id="algo"&gt;Algo&lt;/h2&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Graham scan algorithm:&lt;/strong&gt;&lt;br/&gt;
    * choose p with smallest y coord &lt;br/&gt;
    * &lt;em&gt;sort points by polar angle&lt;/em&gt; with p &lt;br/&gt;
    * consider points in order (stack is used), &lt;em&gt;discard unless creates a ccw turn&lt;/em&gt;.   &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image019.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image020.png"/&gt; &lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image021.png"/&gt; &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;CCW&lt;/strong&gt; &lt;br/&gt;
given three points a b c, returns if a→b→c is a CCW turn.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image023.png"/&gt; &lt;br/&gt;
(assumption: no 3 points on a line)&lt;br/&gt;
 ⇒ calculate &lt;em&gt;cross product of ab and bc ⇒ determinants!&lt;/em&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_2/pasted_image024.png"/&gt; &lt;br/&gt;
area&amp;gt;0 ⇔ CCW   &lt;/p&gt;
&lt;h2 id="implementation_3"&gt;implementation&lt;/h2&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class Point2D{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;private double x,y;&lt;/span&gt;
&lt;span class="code-line"&gt;public static boolean ccw(Point2D a,Point2D b,Point2D c){&lt;/span&gt;
&lt;span class="code-line"&gt;    double area2 = (b.x-a.x)*(c.y-a.y) - (b.y-a.y)*(c.x-a.x);&lt;/span&gt;
&lt;span class="code-line"&gt;    return area2&amp;gt;0;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;convex hull:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;Stack&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;Point2D&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;GrahamScan&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Point2D&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="cm"&gt;/* assumes that points are sorted by polar angle in p[]&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    Stack&amp;lt;Point2D&amp;gt; hull = new Stack&amp;lt;Point2D&amp;gt;();&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    hull.push(p[0]);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    hull.push(p[1]);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    for(int i=2;i&amp;lt;p.length;i++){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        Point2D b = hull.pop(), a = hull.peek(), c = p[i];&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        while(!Point2D.ccw(a,b,c)){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;            b = hull.pop();&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;            a = hull.peek();&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        }&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        //now a,b,c makes a ccw turn:&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        hull.push(b);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;        hull.push(c);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;    }&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="cm"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;running time: &lt;em&gt;NlgN for sorting and linear for the rest.&lt;/em&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 2-1 Stacks and Queues</title><link href="https://x-wei.github.io/notes/algoI_week2_1.html" rel="alternate"/><published>2015-07-09T00:00:00+02:00</published><updated>2015-07-09T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-07-09:/notes/algoI_week2_1.html</id><summary type="html">&lt;p&gt;fundamental data types: stacks and queues
operations: 
&lt;strong&gt;insert, remove, test empy, iterate,&lt;/strong&gt;...  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;module programming: seperate interface and implementation&lt;/p&gt;
&lt;h1 id="1-stacks"&gt;1. Stacks&lt;/h1&gt;
&lt;p&gt;ex. a stack of strings&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;API: &lt;/p&gt;
&lt;p&gt;public interface StackoOfStrings{
    void push(String item);
    String pop();
    boolean isEmpty();
    //int size();
}&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="implementation-1-using-a-linkedlist"&gt;implementation 1: using a linkedlist&lt;/h3&gt;
&lt;p&gt;insert/remove from the top of …&lt;/p&gt;</summary><content type="html">&lt;p&gt;fundamental data types: stacks and queues
operations: 
&lt;strong&gt;insert, remove, test empy, iterate,&lt;/strong&gt;...  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;module programming: seperate interface and implementation&lt;/p&gt;
&lt;h1 id="1-stacks"&gt;1. Stacks&lt;/h1&gt;
&lt;p&gt;ex. a stack of strings&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;API: &lt;/p&gt;
&lt;p&gt;public interface StackoOfStrings{
    void push(String item);
    String pop();
    boolean isEmpty();
    //int size();
}&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="implementation-1-using-a-linkedlist"&gt;implementation 1: using a linkedlist&lt;/h3&gt;
&lt;p&gt;insert/remove from the top of the linkedlist&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;inner class&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="n"&gt;ListNode&lt;/span&gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;String&lt;/span&gt; &lt;span class="nb"&gt;item&lt;/span&gt;;&lt;/span&gt;
&lt;span class="code-line"&gt;    &lt;span class="n"&gt;ListNode&lt;/span&gt; &lt;span class="nb"&gt;next&lt;/span&gt;;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;implementation  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;LinkedStackOfStrings&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;StackoOfStrings&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;ListNode&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nxt&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;LinkedStackOfStrings&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;firstItem&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;firstItem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;complexity: const time for every operation&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="array-implementation"&gt;array implementation&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;use array (of length N) to store items → defect: stack has limited capacity&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;keep a pointer &lt;em&gt;top: &lt;/em&gt;&lt;strong&gt;pointing to the next empty space to push &lt;/strong&gt;(top 的定义很重要)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;problems of the array implementation: &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;underflow: pop from an empty stack  &lt;/li&gt;
&lt;li&gt;overflow: size larger than capacity ⇒ resizing  &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;loitering&lt;/strong&gt;: holding a ref to an obj which is no longer needed:
ex. &lt;code&gt;return s[top--]&lt;/code&gt;
java system will not know that s[top] is no longer needed ⇒ have to clear it explicitely
⇒   &lt;/p&gt;
&lt;p&gt;String item = s[top--]; 
s[top]=null; 
return item&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;implementation (containg resizing array operations)  &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ArrayStackOfStrings&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;StackOfStrings&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ArrayStackOfStrings&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;to&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;be&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;tuned&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;initial&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;vois&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;helper&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;functoin&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;capacity&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;s2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;doubling&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;size&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;lenth&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;top++&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;pop&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;--top&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="ow"&gt;NOT&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="c1"&gt;--!&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;top&lt;/span&gt;&lt;span class="o"&gt;]=&lt;/span&gt;&lt;span class="k"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="k"&gt;top&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;necessary&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="2-resizing-arrays_1"&gt;2. Resizing Arrays&lt;/h1&gt;
&lt;p&gt;resolving the overflow pb: grow and shrink the array
→ need to copy all items when changing array size
⇒ pb: &lt;em&gt;ensure that sizing happens infrequently&lt;/em&gt;&lt;/p&gt;
&lt;h3 id="resizing-strategy"&gt;resizing strategy&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;repeated doubling:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(initial capacity=1) when array is full, double the size&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;amortized&lt;/em&gt; complexity for inserting N:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;N+(2+4+8+...+N) ~3N&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;shrinking array&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;⇒ shrink the array by half when array is &lt;strong&gt;1/4 full&lt;/strong&gt;
not half full → &lt;em&gt;thrashing&lt;/em&gt; will happen if push-pop-push-pop when array is full &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image001.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;[invariant]&lt;/strong&gt;: array always 20%~100% full&lt;/li&gt;
&lt;li&gt;complexity:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;em&gt;in an amortized sense&lt;/em&gt;, will be constant &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image002.png"/&gt; &lt;br/&gt;
&lt;strong&gt;proposition&lt;/strong&gt;: from empty stack, M operations of push/pop taked time propotional to M&lt;/p&gt;
&lt;h3 id="comparison-resizable-array-vs-linkedlist"&gt;comparison: resizable array vs linkedlist&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;linkedlist implementation: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;operations takes const time even in worst time
extra time and space for dealing with linkes &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;resizing array implementation:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;operation taked const &lt;em&gt;amortized&lt;/em&gt; time
but in worst case takes linear time (ex. to be evited for critical systems)
less wasted space&lt;/p&gt;
&lt;h2 id="3-queues_1"&gt;3. Queues&lt;/h2&gt;
&lt;p&gt;FIFO data structure
API&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public interface QueueOfStrings{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    void enqueue(String item);&lt;/span&gt;
&lt;span class="code-line"&gt;    String dequeue();&lt;/span&gt;
&lt;span class="code-line"&gt;    boolean isEmpty();&lt;/span&gt;
&lt;span class="code-line"&gt;    //int size();&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="linked-list-implementation"&gt;linked list implementation&lt;/h3&gt;
&lt;p&gt;maintain &lt;code&gt;first&lt;/code&gt; and &lt;code&gt;last&lt;/code&gt; node pointers: 
pointing to 2 points of queue (&lt;code&gt;first&lt;/code&gt; for dequeue, &lt;code&gt;last&lt;/code&gt; for enqueue ) &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image003.png"/&gt; &lt;br/&gt;
→ &lt;em&gt;take care of corner cases&lt;/em&gt;: 
- empty queue: first is null (and last is also null) 
- just one item in queue: first and last &lt;em&gt;point to the same node&lt;/em&gt;
(总之first和last的定义很重要)&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;LinkedQueueOfStrings&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;QueueOfStrings&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="w"&gt;  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;LinkedQueueOfStrings&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;enqueue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;&lt;span class="c1"&gt;//same as push&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Node&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;nd&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;dequeue&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;span class="c1"&gt;//same as pop in stack&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nx"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;firstItem&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nx"&gt;last&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;firstItem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;(){&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="nx"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="resizing-array-implementation"&gt;resizing array implementation&lt;/h3&gt;
&lt;p&gt;maintain &lt;code&gt;head&lt;/code&gt; and &lt;code&gt;tail&lt;/code&gt;: 
&lt;code&gt;head&lt;/code&gt; is the queue head, &lt;code&gt;tail&lt;/code&gt; is the &lt;em&gt;next empty position&lt;/em&gt; for the next element to enqueue
→ trick: head and tail should take &lt;em&gt;mod capacity + &lt;/em&gt;resizing array &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image004.png"/&gt; &lt;br/&gt;
不知道写的对不对: &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;ArrayQueueOfStrings&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;QueueOfStrings&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="err"&gt;[]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;LinkedQueueOfStrings&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;1&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="n"&gt;init&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;capacity&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;isEmpty&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;newsz&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;q2&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;newsz&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;q2&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j++&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;enqueue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;dequeue&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;String&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;firstItem&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sz&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tail&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;head&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;%&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sz&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;sz&lt;/span&gt;&lt;span class="o"&gt;==&lt;/span&gt;&lt;span class="n"&gt;q&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="n"&gt;resize&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;s&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;length&lt;/span&gt;&lt;span class="o"&gt;/&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;firstItem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h1 id="4-generics_2"&gt;4. Generics&lt;/h1&gt;
&lt;p&gt;queues/stacks for other types of data ⇒ &lt;em&gt;generics 泛型&lt;/em&gt;(java 1.5 才引进泛型机制...)
use &lt;em&gt;type paramater&lt;/em&gt;→ avoid casting, and discover type mismatch errors &lt;em&gt;at compile time&lt;/em&gt; &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;    public interface Stack&amp;lt;Item&amp;gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;        public void push(Item item);&lt;/span&gt;
&lt;span class="code-line"&gt;        public Item pop();&lt;/span&gt;
&lt;span class="code-line"&gt;        public boolean isEmpty();&lt;/span&gt;
&lt;span class="code-line"&gt;    }&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="a-pb-with-array-implementation"&gt;a pb with array implementation&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;java不支持创立泛型数组&lt;/strong&gt;
generic array creation is not allowed. 不可以new 一个泛型数组!
&lt;code&gt;s = new Item[capacity];&lt;/code&gt;会报错 &lt;br/&gt;
⇒ use an ugly &lt;em&gt;cast&lt;/em&gt;:
&lt;code&gt;s = (Item[]) new Object[capacity];&lt;/code&gt;
(will get warning: "unchecked cast" → java被黑了... )&lt;/p&gt;
&lt;h3 id="autoboxing-for-primitive-types"&gt;autoboxing for primitive types&lt;/h3&gt;
&lt;p&gt;each primitive type has a &lt;em&gt;wrapper class&lt;/em&gt;
ex. int ↔ Integer
autoboxing: automatic cast between a primitive type and its wrapper class. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image005.png"/&gt; &lt;br/&gt;
(syntactic sugar 语法糖 i.e. 对语言功能没有影响只是方便使用)&lt;br/&gt;
btw: &lt;a href="https://zh.wikipedia.org/wiki/%E8%AF%AD%E6%B3%95%E7%B3%96"&gt;https://zh.wikipedia.org/wiki/%E8%AF%AD%E6%B3%95%E7%B3%96&lt;/a&gt; (居然还有语法盐和语法糖精......)&lt;/p&gt;
&lt;h1 id="5-iterators_1"&gt;5. Iterators&lt;/h1&gt;
&lt;h3 id="interface"&gt;Interface&lt;/h3&gt;
&lt;p&gt;support iteration over stacks and queues, &lt;em&gt;without revealing the internal representation&lt;/em&gt; of stack/queue
⇒ implement the &lt;code&gt;Iterable&lt;/code&gt; interface&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;Iterable&lt;/code&gt; interface: can return an *Iterator *&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public interface Iterable{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;    Iterator&amp;lt;Item&amp;gt; iterator();&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Iterator interface: hasNext() and next() interface&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;interface&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Iterator&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;Item&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;hasNext&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;Item&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;next&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;remove&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="c1"&gt;;//optional, bad practice to use it&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;to make a data structure Interable → elegant client code   &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image006.png"/&gt; &lt;br/&gt;
&lt;strong&gt;how-to:&lt;/strong&gt;&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;implement &lt;code&gt;Iterable&lt;/code&gt; interface&lt;/li&gt;
&lt;li&gt;write a &lt;em&gt;private inner class&lt;/em&gt; XXIterator that implment the &lt;code&gt;Iterator&lt;/code&gt; interface.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;ex. &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;h3 id="bag-data-structure"&gt;Bag data structure&lt;/h3&gt;
&lt;p&gt;Supports adding and iterating through without caring about the order.&lt;br/&gt;
API: &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kd"&gt;class&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Item&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Bag&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;implements&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;Iterable&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Item&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Item&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="nx"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;size&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;can be implemented by stack or queue(without pop/dequeue)&lt;/p&gt;
&lt;h1 id="6-applications_1"&gt;6. Applications&lt;/h1&gt;
&lt;h3 id="java-collections-library"&gt;Java collections library&lt;/h3&gt;
&lt;p&gt;List interface: &lt;code&gt;java.util.List&lt;/code&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image008.png"/&gt; &lt;br/&gt;
implementations: &lt;code&gt;ArrayList&lt;/code&gt;, &lt;code&gt;LinkedList&lt;/code&gt;. &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;pb with the java's implementation of stacks and queues:  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code&gt;Stack&lt;/code&gt; class also implements List interface (&lt;code&gt;get()&lt;/code&gt;, &lt;code&gt;remove()&lt;/code&gt;, &lt;code&gt;contains()&lt;/code&gt; are implemented);&lt;br/&gt;
&lt;code&gt;Queue&lt;/code&gt; is an interface rather than a class...&lt;br/&gt;
⇒ **poorly designed API  **&lt;/p&gt;
&lt;h3 id="stacks-applications"&gt;Stacks applications&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;function calls: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image009.png"/&gt; &lt;br/&gt;
recursion: can always use an explicit stack to remove recursion&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;arithemic evaluation (Dijkstra)  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;四种类型: 左括号, 右括号, 数字, 算子  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image010.png"/&gt;&lt;br/&gt;
最后一行应该是value stack.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week2_1/pasted_image011.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ 后缀表达式, 逆波兰式......&lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week1-Lab: Percolation</title><link href="https://x-wei.github.io/notes/algoI_week1_lab.html" rel="alternate"/><published>2015-07-07T00:00:00+02:00</published><updated>2015-07-07T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-07-07:/notes/algoI_week1_lab.html</id><summary type="html">&lt;h1 id="model-problem"&gt;model &amp;amp; problem&lt;/h1&gt;
&lt;p&gt;(原文描述太啰嗦了)&lt;br/&gt;
A system using an N-by-N grid of sites. &lt;br/&gt;
→ Each site is either open or blocked. &lt;br/&gt;
→ A &lt;strong&gt;full&lt;/strong&gt; site is an open site that can be connected to an open site in the top row via a chain of neighboring open …&lt;/p&gt;</summary><content type="html">&lt;h1 id="model-problem"&gt;model &amp;amp; problem&lt;/h1&gt;
&lt;p&gt;(原文描述太啰嗦了)&lt;br/&gt;
A system using an N-by-N grid of sites. &lt;br/&gt;
→ Each site is either open or blocked. &lt;br/&gt;
→ A &lt;strong&gt;full&lt;/strong&gt; site is an open site that can be connected to an open site in the top row via a chain of neighboring open sites. (这个full的定义有玄机 而且导致后面写程序时有个问题, 看论坛想了半天才想出来, 见后文.)&lt;br/&gt;
→ We say the system &lt;strong&gt;percolates&lt;/strong&gt; if there is a path of connected open sites form the top row to the bottom row.   &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image.png"/&gt; &lt;/p&gt;
&lt;p&gt;⇒ pb: if sites are independently set to be open with probability &lt;strong&gt;p&lt;/strong&gt;, what is the probability that the system percolates? &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image001.png"/&gt; &lt;br/&gt;
→ When N is sufficiently large, there is a threshold value &lt;strong&gt;p&lt;/strong&gt;&lt;em&gt; such that when p &amp;lt; p&lt;/em&gt; a random N-by-N grid almost never percolates, and when p &amp;gt; p&lt;em&gt;, a random N-by-N grid almost always percolates. &lt;br/&gt;
→ No mathematical solution for determining the percolation threshold p&lt;/em&gt; has yet been derived. &lt;br/&gt;
⇒ Your task is to &lt;em&gt;write a computer program to estimate p&lt;/em&gt;*.   &lt;/p&gt;
&lt;h1 id="method"&gt;Method&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;API:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;class&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Percolation&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;Percolation&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt;               &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;create&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nv"&gt;by&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="nv"&gt;N&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;grid&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;with&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;all&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;sites&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;blocked&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;open&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt;          &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;open&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;site&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;row&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;column&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;it&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;not&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;open&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;already&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;isOpen&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;site&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;row&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;column&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;open&lt;/span&gt;?&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;isFull&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt;     &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;is&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;site&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;row&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;,&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;column&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;j&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;full&lt;/span&gt;?&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;boolean&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;percolates&lt;/span&gt;&lt;span class="ss"&gt;()&lt;/span&gt;&lt;span class="w"&gt;             &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;does&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;the&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;system&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;percolate&lt;/span&gt;?&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="nv"&gt;public&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;static&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;void&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;main&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;String&lt;/span&gt;[]&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;args&lt;/span&gt;&lt;span class="w"&gt;   &lt;/span&gt;&lt;span class="o"&gt;//&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;test&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nv"&gt;client&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="nv"&gt;optional&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Corner cases: the row and column indices i and j are integers between 1 and N. &lt;strong&gt;1≤i,j≤N&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;if i/j out of range: &lt;code&gt;java.lang.IndexOutOfBoundsException&lt;/code&gt;
if N&amp;lt;=0 in constructor: &lt;code&gt;java.lang.IllegalArgumentException&lt;/code&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Performance requirements: N2 for constructor, const for other operations&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Monte Carlo simulation&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;all sites init to be closed&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ randomly choose a blocked site (i,j) and open it 
→ &lt;em&gt;repeat until percolates&lt;/em&gt; ⇒ the fraction of opened sites is an estimation of p*&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;ex. 20*20 grid, when percolated: &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image002.png"/&gt; &lt;br/&gt;
⇒ estimated p* = 204/400=0.51&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;repeat the estimation for T times, get T estimations &lt;/p&gt;
&lt;p&gt;→ get mean and std:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image003.png"/&gt; &lt;br/&gt;
→ 95% 置信区间: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image004.png"/&gt; &lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;create API for this simulation: &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public class PercolationStats {&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;   public PercolationStats(int N, int T)     // perform T independent experiments on an N-by-N grid&lt;/span&gt;
&lt;span class="code-line"&gt;   public double mean()                      // sample mean of percolation threshold&lt;/span&gt;
&lt;span class="code-line"&gt;   public double stddev()                    // sample standard deviation of percolation threshold&lt;/span&gt;
&lt;span class="code-line"&gt;   public double confidenceLo()              // low  endpoint of 95% confidence interval&lt;/span&gt;
&lt;span class="code-line"&gt;   public double confidenceHi()              // high endpoint of 95% confidence interval&lt;/span&gt;
&lt;span class="code-line"&gt;   public static void main(String[] args)    // test client (described below)&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;-if  N ≤ 0 or T ≤ 0: &lt;code&gt;java.lang.IllegalArgumentException&lt;/code&gt;&lt;br/&gt;
-&lt;code&gt;main()&lt;/code&gt; : takes two command-line arguments N and T&lt;br/&gt;
⇒ performs T independent computational experiments on an N-by-N grid, and prints out the mean, standard deviation, and the 95% confidence interval for p*. &lt;br/&gt;
(Use &lt;a href="http://introcs.cs.princeton.edu/java/stdlib/javadoc/StdRandom.html"&gt;standard random&lt;/a&gt; from our standard libraries to generate random numbers; use &lt;a href="http://introcs.cs.princeton.edu/java/stdlib/javadoc/StdStats.html"&gt;standard statistics&lt;/a&gt; to compute the sample mean and standard deviation. &lt;br/&gt;
Here is the algo API: &lt;a href="http://algs4.cs.princeton.edu/code/index.php"&gt;http://algs4.cs.princeton.edu/code/index.php&lt;/a&gt;)  &lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h1 id="code"&gt;Code&lt;/h1&gt;
&lt;p&gt;注意一定要用它们提供的那些库, 否则自己写的话代码就长了.... &lt;br/&gt;
shuffle, mean, stddev什么的直接用他们的函数库就可以做到. &lt;br/&gt;
&lt;a href="http://algs4.cs.princeton.edu/code/index.php"&gt;http://algs4.cs.princeton.edu/code/index.php&lt;/a&gt; &lt;br/&gt;
另外UF也是用他们写好的, WeightedQuickUnionUF.   &lt;/p&gt;
&lt;p&gt;按照提示, 除了格子的N^2个节点以外再增加两个节点: 顶部和底部的虚拟节点. 这里写的时候注意一开始也是不恩能够把它们与第一行/最后一行相连的 — 要在一个格子open以后再相连. &lt;/p&gt;
&lt;h3 id="backwash"&gt;backwash问题&lt;/h3&gt;
&lt;p&gt;这次题目有一点比较困难就是, 需要实现isFull()函数, 这个函数判断一个格子(i,j)是否和顶部相连. 这里如果直接用UF的connected()判断是否和顶部虚拟节点相连的话是有问题的, 如下图: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/file:///home/wx/Dropbox/ZIM_NOTES/0._TmpNotes/Algorithms%2C_4th_ed/Week1-Assignment-Percolation/pasted_image005.png"/&gt; &lt;br/&gt;
白色格子表示格子是open的, 蓝色格子表示格子是open并且是&lt;em&gt;full&lt;/em&gt;的(i.e. 和顶部相连的), 左边图片里的状态是对的, 右边图片里底下部分的格子状态则不对: 如左下角的格子, 其实是没有和顶部联通的, 如果我们用两个虚拟节点的话, 由于底部虚拟节点和顶部虚拟节点相连, 所以和底部虚拟节点相连的左下角部分就被判断成了full的. &lt;/p&gt;
&lt;p&gt;这个问题一开始我以为可以很简单解决, 后来发现没那么容易... (注意题目还要求isFull()也要在常数时间给出结果).&lt;br/&gt;
一个不优雅的办法是, 建立两个UF, 一个用来判断percolation, 另一个UF里没有底部虚拟节点所以可以专门用来判断isFull(). &lt;/p&gt;
&lt;p&gt;这样解决的话使可以通过测试, 不过非常不好看, 另外一个UF的内存占用是8N^2(内部有size[]和id[]两个int数组), 比较大. &lt;/p&gt;
&lt;p&gt;在论坛上找了半天, 看了一些人的分享终于想到了这个非常妙的办法: &lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;UF只建立顶部虚拟节点, 不建立底部虚拟节点. &lt;/li&gt;
&lt;li&gt;判断isFull只需要用UF的connected()一下就好了&lt;/li&gt;
&lt;li&gt;问题是怎么判断percolation: &lt;br/&gt;
    a. 建立一个数组 &lt;code&gt;boolean connectedToBottom[]&lt;/code&gt;, 指示某一点是否和底部相连 &lt;br/&gt;
    b. trick在这里: 不必修改一个联通分支的所有点的&lt;code&gt;connectedToBottom&lt;/code&gt;的值, &lt;strong&gt;只需要修改联通分支的root(UF的find)即可&lt;/strong&gt;. 在进行union的时候先查看两个component的root是不是连到底部, 然后有一个连到底部的话, 在union以后把合并后的联通分支的&lt;code&gt;connectedToBottom&lt;/code&gt;状态改为true即可 &lt;br/&gt;
    c. 然后判断percolate: 先找到顶部虚拟节点锁在component的root, 然后看这个root是否连到底部即可!   &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;这样用一个boolean数组(N^2内存)代替了一个新的UF(8N^2内存), 而且实现也更加优雅.  &lt;br/&gt;
非常有意思的练习...&lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 1-2 Analysis of Algorithms</title><link href="https://x-wei.github.io/notes/algoI_week1_2.html" rel="alternate"/><published>2015-07-02T00:00:00+02:00</published><updated>2015-07-02T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-07-02:/notes/algoI_week1_2.html</id><summary type="html">&lt;h1 id="1-introduction"&gt;1. Introduction&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image.png"/&gt;&lt;/p&gt;
&lt;h1 id="2-observations"&gt;2. Observations&lt;/h1&gt;
&lt;p&gt;ex. &lt;strong&gt;3-SUM pb&lt;/strong&gt;&lt;br/&gt;
&lt;em&gt;given N distinct numbers, how many triples sum up to 0? (pb related to computatioal geogtry)&lt;/em&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;brute force method:&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="k"&gt;if …&lt;/span&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</summary><content type="html">&lt;h1 id="1-introduction"&gt;1. Introduction&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image.png"/&gt;&lt;/p&gt;
&lt;h1 id="2-observations"&gt;2. Observations&lt;/h1&gt;
&lt;p&gt;ex. &lt;strong&gt;3-SUM pb&lt;/strong&gt;&lt;br/&gt;
&lt;em&gt;given N distinct numbers, how many triples sum up to 0? (pb related to computatioal geogtry)&lt;/em&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;brute force method:&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;        &lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;N&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="o"&gt;]+&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;k&lt;/span&gt;&lt;span class="o"&gt;]==&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;                &lt;/span&gt;&lt;span class="nf"&gt;count&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;            &lt;/span&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;mesuring running time:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;stdlib.jar里面提供了一个&lt;code&gt;Stopwatch&lt;/code&gt;类用于记录运行时间.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image001.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;log-log plot&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;T(N) = running time for input of size N&lt;br/&gt;
log(N)-log(T(N)) plot:&lt;br/&gt;
often get a straight line — power law  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image002.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;doubling ratio&lt;/strong&gt;:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(for checking the power law relationship, checking the power order)&lt;br/&gt;
each time double the size of input, then take log of the time ratio of 2 runs: log( T(2N)/T(N) )  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image003.png"/&gt; &lt;/p&gt;
&lt;h1 id="3mathematical-models"&gt;3.Mathematical Models&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;total running time: sum of cost*frequency of operations &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;cost of some basic operations:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;array allocation: c*N (because all array entries have to be set to 0/false/null)&lt;/li&gt;
&lt;li&gt;string concatenation: c*N (proportional to the length  of string !)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;simplification&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;crude analysis&lt;br/&gt;
ignore lower terms &lt;strong&gt;tilde notation&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image005.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image004.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;estimating discrete sum by relaxation&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Replace the sum with an integral, and use calculus — 很机智...   &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image006.png"/&gt;&lt;/p&gt;
&lt;h1 id="4-order-of-growth-classification"&gt;4. Order of Growth Classification&lt;/h1&gt;
&lt;p&gt;(discard the leading coefficient when considering the growth order)&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;only a small set of growth functions: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code&gt;1, logN, N, NlogN, N^2, N^3, 2^N&lt;/code&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image007.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;exemples:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;binary search ⇒ logN&lt;br/&gt;
divide and conquer ⇒ NlogN&lt;br/&gt;
exhaustive search ⇒ 2^N &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image008.png"/&gt;&lt;/p&gt;
&lt;p&gt;practical performance: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image009.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;ex. &lt;strong&gt;binary search&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;public int binearch(int arr[], int key){//arr[] already sorted
    int lo=0,hi=arr.length;
    while(i&amp;lt;j){
        int m = (lo+hi)/2;
        if(arr[m]==key) return m;
        else if(arr[m]&amp;lt;key) lo=m+1;
        else hi=m-1;
    }
    return -1;
}&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;(→ Bug in Java's Arrays.binarySearch() discovered in 2006......) &lt;br/&gt;
→ invariant: if key in arr, arr[lo]&amp;lt;=key&amp;lt;=arr[hi] &lt;br/&gt;
&lt;strong&gt;proposition. &lt;/strong&gt;binary search uses at most logN+1 compares to search a sorted array of size N.
&lt;em&gt;&lt;em&gt;pf. **
denote &lt;/em&gt;T(N)&lt;/em&gt; := nb of compares for array with size &amp;lt;=N&lt;br/&gt;
→ T(1)=1&lt;br/&gt;
→ recurrence relation: T(N)&amp;lt;=T(N/2)+1&lt;br/&gt;
⇒ T(N)=logN  &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;a faster 3-SUM&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ first sort the array &lt;em&gt;(~NlogN)&lt;/em&gt;&lt;br/&gt;
→ for any pair a[i] and a[j], do binary search for -(a[i]+a[j])   &lt;em&gt;~(N2LogN)&lt;/em&gt;&lt;br/&gt;
⇒ reduce from N3 to N2logN ! (for 8k numbers, running time goes from 51s to 0.96s)  &lt;/p&gt;
&lt;h1 id="5-theory-of-algorithms"&gt;5. Theory of Algorithms&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;types of analysis&lt;/p&gt;
&lt;p&gt;-best case
-worst case
-average case(random input, "expected cost")&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;notations&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;big Theta/big O/big Omega&lt;/strong&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image010.png"/&gt; &lt;br/&gt;
    - big O: &lt;em&gt;upper bound  → * once a specific algo is found, find an upper bound&lt;br/&gt;
    - big Omega: &lt;/em&gt;lower bound   &lt;em&gt;→ proove that no algo can do better&lt;br/&gt;
    - big Theta: symptotic growth (same order, optimal algo)  → lower and upper bound &lt;/em&gt;match* &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image011.png"/&gt; &lt;br/&gt;
⇒ in this course: use tilde notation: contain leading constants for highest order term&lt;/p&gt;
&lt;h1 id="6-memory"&gt;6. Memory&lt;/h1&gt;
&lt;p&gt;KB: 2^10 bytes&lt;br/&gt;
MB: 2^20 bytes (1 million) 
GB: 2^30 bytes (1 billion) 
64-bit machines: &lt;em&gt;8 byte pointers&lt;/em&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;typical memory usage:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;for primary types: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image012.png"/&gt;&lt;br/&gt;
for arrays  (with &lt;em&gt;array overhead=24bytes&lt;/em&gt;) :  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image013.png"/&gt; &lt;br/&gt;
&lt;em&gt;Obj overhead: 16 bytes&lt;/em&gt; (obj的大小=16+obj内部filed的大小)&lt;br/&gt;
&lt;em&gt;references&lt;/em&gt;: 8 bytes (ex. inner class has a ref to encolsing class)&lt;br/&gt;
&lt;em&gt;padding&lt;/em&gt;: each obj uses a multiply of 8 bytes (obj大小=8 bytes的整数倍)    &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image014.png"/&gt; &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_2/pasted_image015.png"/&gt; &lt;/p&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>[Algorithms I] Week 1-1 Union-Find</title><link href="https://x-wei.github.io/notes/algoI_week1_1.html" rel="alternate"/><published>2015-06-27T00:00:00+02:00</published><updated>2015-06-27T00:00:00+02:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-06-27:/notes/algoI_week1_1.html</id><summary type="html">&lt;h1 id="1-dynamic-connectivity-pb"&gt;1. Dynamic Connectivity pb&lt;/h1&gt;
&lt;h3 id="pb-statement"&gt;pb statement&lt;/h3&gt;
&lt;p&gt;a set of N obj, &lt;em&gt;indexed by 0,1,...,N-1&lt;/em&gt;
⇒ 
* UNION: connect objects &lt;code&gt;void union(int p, int q)&lt;/code&gt;
* FIND: is there a path connecting 2 obj?  &lt;code&gt;boolean connected(int p, int q)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;ex: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image.png"/&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;connect components&lt;/strong&gt;(联通分支): max set of obj …&lt;/p&gt;</summary><content type="html">&lt;h1 id="1-dynamic-connectivity-pb"&gt;1. Dynamic Connectivity pb&lt;/h1&gt;
&lt;h3 id="pb-statement"&gt;pb statement&lt;/h3&gt;
&lt;p&gt;a set of N obj, &lt;em&gt;indexed by 0,1,...,N-1&lt;/em&gt;
⇒ 
* UNION: connect objects &lt;code&gt;void union(int p, int q)&lt;/code&gt;
* FIND: is there a path connecting 2 obj?  &lt;code&gt;boolean connected(int p, int q)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;ex: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image.png"/&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;connect components&lt;/strong&gt;(联通分支): max set of obj that are mutually connected. &lt;/p&gt;
&lt;h3 id="uf-api"&gt;UF API&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;union(p,q): connect 2 obj&lt;/li&gt;
&lt;li&gt;connected(p,q): test if p and q are connected &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;find(p)&lt;/strong&gt;: find the &lt;em&gt;component id&lt;/em&gt; of p&lt;/li&gt;
&lt;li&gt;count(): nb of components&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;注意:
命名不是很好, 这里的&lt;code&gt;find()&lt;/code&gt;函数不对应FIND query, &lt;code&gt;connected()&lt;/code&gt;函数才是真正的FIND query, find()函数是为了connected()函数而做的一个辅助函数(find(p): return the root of the node p )
在connected里就可以调用find: &lt;code&gt;return find(p)==find(q)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;应该是interface更好一些... &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;public interface UF{&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;void union(int p, int q);&lt;/span&gt;
&lt;span class="code-line"&gt;boolean connected(int p, int q);&lt;/span&gt;
&lt;span class="code-line"&gt;//int find(int p);&lt;/span&gt;
&lt;span class="code-line"&gt;//int count();&lt;/span&gt;
&lt;span class="code-line"&gt;}&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;测试client: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image003.png"/&gt;&lt;/p&gt;
&lt;h1 id="2-quick-find_1"&gt;2. Quick Find&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;"eager approach"&lt;/em&gt;&lt;/p&gt;
&lt;h3 id="data-structure"&gt;data structure&lt;/h3&gt;
&lt;p&gt;⇒ an int array &lt;code&gt;id[]&lt;/code&gt;
initialized to &lt;em&gt;id[p]=p for all p&lt;/em&gt;
interpretation: &lt;em&gt;id[p] = &lt;/em&gt;&lt;strong&gt;component id of obj p&lt;/strong&gt;&lt;em&gt;
⇒ p and q are connected &lt;/em&gt;iff* id[p]==id[q] (ie. find very fast)
没有用find()函数  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image002.png"/&gt; &lt;/p&gt;
&lt;h3 id="uf-operations"&gt;UF operations&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;FIND:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code&gt;connected(p,q):&lt;/code&gt; very fast, just check id[p] and id[q]&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;UNION:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;when merging 2 components :
&lt;code&gt;union(p,q)&lt;/code&gt;: &lt;code&gt;id[p]=id[q]&lt;/code&gt;(总是让第一个参数p的id变为第二个参数q的id), &lt;br/&gt;
⇒ then have to modify &lt;em&gt;all entries&lt;/em&gt; with id equal to &lt;code&gt;id[p]&lt;/code&gt; !&lt;br/&gt;
⇒ too many entries to change  &lt;/p&gt;
&lt;h3 id="implementation"&gt;implementation&lt;/h3&gt;
&lt;p&gt;&lt;em&gt;(class  QuickFindUF implements UF)&lt;/em&gt;&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image004.png"/&gt;&lt;/p&gt;
&lt;p&gt;complexity: &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;FIND: cte&lt;/li&gt;
&lt;li&gt;UNION: lin...&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;if N obj + N unions ⇒ &lt;em&gt;quad time !&lt;/em&gt;&lt;br/&gt;
btw, 程序运行速度: &lt;strong&gt;~10^9/s&lt;/strong&gt;&lt;/p&gt;
&lt;h1 id="3-quick-union_1"&gt;3. Quick Union&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;"lazy approach"&lt;/em&gt;&lt;/p&gt;
&lt;h3 id="data-structure_1"&gt;data structure&lt;/h3&gt;
&lt;p&gt;⇒ also an int array &lt;code&gt;id[]&lt;/code&gt;
considering a set of &lt;em&gt;trees, &lt;/em&gt;此时每个联通分支都是一个tree&lt;br/&gt;
interpretation: &lt;em&gt;id[p] = &lt;/em&gt;&lt;strong&gt;parent index of obj p &lt;/strong&gt;(觉得这个数组叫做father更好....)&lt;br/&gt;
⇒ p is a root node &lt;em&gt;iff&lt;/em&gt; id[p]==p&lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image005.png"/&gt;&lt;/p&gt;
&lt;h3 id="uf-operations_1"&gt;UF operations&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;FIND:&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code&gt;connected(p,q):&lt;/code&gt;check if &lt;em&gt;root of p == root of q&lt;/em&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;UNION: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;code&gt;union(p,q):&lt;/code&gt;just set p's root to be &lt;em&gt;child&lt;/em&gt; of q's root (把第一个参数p的那棵树放入第二个参数q的树的根节点作为子树)&lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image006.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;root():&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;前两个的操作都需要一个函数查找一个节点的root,  需要写一个函数实现, 也很简单, 一路找parent即可:   &lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre&gt;&lt;span class="code-line"&gt;&lt;span&gt;&lt;/span&gt;&lt;code&gt;&lt;span class="n"&gt;private&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;root&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;int&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;{&lt;/span&gt;&lt;/code&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;span class="err"&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class="code-line"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h3 id="implementation_1"&gt;implementation&lt;/h3&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image007.png"/&gt;&lt;/p&gt;
&lt;h3 id="complexity"&gt;complexity&lt;/h3&gt;
&lt;p&gt;in the worst case (all elements is in a list form), root() is ~N, so:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;FIND: lin&lt;/li&gt;
&lt;li&gt;UNION: lin&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;quick find和quick union的问题: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image009.png"/&gt;&lt;/p&gt;
&lt;h1 id="4-quick-union-improvements_1"&gt;4. Quick Union Improvements&lt;/h1&gt;
&lt;h2 id="improvement1-weighting"&gt;improvement1: weighting&lt;/h2&gt;
&lt;p&gt;&lt;em&gt;keep track of tree size&lt;/em&gt; ⇒ balance by taking the small tree be a child of the large tree  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image010.png"/&gt;&lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image011.png"/&gt;&lt;/p&gt;
&lt;p&gt;⇒ add an extra array: &lt;code&gt;sz[]&lt;/code&gt; sz[i] is the size of the tree with root i&lt;/p&gt;
&lt;h3 id="implementation_2"&gt;implementation&lt;/h3&gt;
&lt;p&gt;(数组&lt;code&gt;int  sz[]&lt;/code&gt; 初始全部为1)&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;依然需要&lt;code&gt;root()&lt;/code&gt;函数.&lt;/p&gt;
&lt;p&gt;private int root(int p){
    while(p!=id[p]) p=id[p];
    return p;
}&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;FIND &lt;/p&gt;
&lt;p&gt;public boolean connected(int p, int q){
    return root(p)==root(q);
}&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;UNION&lt;/p&gt;
&lt;p&gt;public void  union(int p, int q){
    int rp = root(p), rq=root(q);
    if(rp==rq) return; // 
    if (sz[rp]&amp;lt;sz[rq]){
        id[rp]=rq;
        sz[rq]+=sz[rp];
    }
    else{...}
}&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="complexity_1"&gt;complexity&lt;/h3&gt;
&lt;p&gt;FIND: proportional to &lt;em&gt;depth of p and&lt;/em&gt; q in their tree
UNION: const if p and q are root&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;proposition&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;the max depth of weightedQuickUnion is &lt;strong&gt;lgN&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;[pf] considering a node &lt;code&gt;x&lt;/code&gt;, in tree &lt;code&gt;T1&lt;/code&gt;, &lt;code&gt;dep(x)&lt;/code&gt; is x's depth in its tree.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image012.png"/&gt; &lt;br/&gt;
→   &lt;code&gt;dep(x)&lt;/code&gt; will increase by 1, iff &lt;code&gt;T1&lt;/code&gt; is merged into another tree &lt;code&gt;T2&lt;/code&gt; (and by the algo, shoud have |T1|&amp;lt;=|T2| )&lt;br/&gt;
→   x's tree's size become |T1|+|T2| &amp;gt;= 2&lt;em&gt;|T1| 
⇒   everytime dep(x) increased by 1, x's tree's size will &lt;/em&gt;at least double*&lt;br/&gt;
at first dep(x)=1, if dep(x) increases lgN times, the size of the tree will be &amp;gt;=  N &lt;br/&gt;
CQFD.&lt;/p&gt;
&lt;p&gt;so the &lt;code&gt;root()&lt;/code&gt; function takes only lgN time. 
&lt;strong&gt;conclusion&lt;/strong&gt;: both UNION and FIND will be in &lt;strong&gt;lgN &lt;/strong&gt;time. &lt;/p&gt;
&lt;h2 id="improvement-2-path-compression_1"&gt;improvement 2: path compression&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;imporve the root() function: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;when looking for root of a node ⇒ link &lt;em&gt;all nodes in the path &lt;/em&gt;up to the root. &lt;br/&gt;
⇒ just a constant extra time compared to old implementation. &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;2 pass implementation: &lt;/p&gt;
&lt;p&gt;private int root(int p){
    int r = p;
    while(r!=id[r]) r=id[r];
    while(p!=r){
        int t = p;
        p=id[p];
        id[t]=r;
    }
    return r;
}&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;flatens the tree greatly. &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;single pass implementation: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;just make all other node &lt;em&gt;point to its grandparent&lt;/em&gt; (halving the path length)
⇒ not as flatening as before, but in practice will almost be the same. 
just one extra line of code: 
    private int root(int p){
        while(p!=id[p]){ 
            id[p] = id[ id[p] ];
            p=id[p];  &lt;br/&gt;
        }
        return p;
    }&lt;/p&gt;
&lt;h3 id="complexity_2"&gt;complexity&lt;/h3&gt;
&lt;p&gt;(for weighet quick union with path compression — &lt;em&gt;WQUPC&lt;/em&gt;)&lt;br/&gt;
very very small: &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image013.png"/&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;lg*()&lt;/strong&gt; function: "&lt;em&gt;iterated log function&lt;/em&gt;", lg&lt;em&gt;(N) = the number of time to take log to get to 1
lg&lt;/em&gt;()几乎可以看成常数了:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image014.png"/&gt; &lt;br/&gt;
ex. &lt;em&gt;lg&lt;/em&gt;(65536) = 4&lt;em&gt; (x^16=65536)&lt;br/&gt;
because: lg(65536)=16 ; lg(16) = 4; lg(4)=2; lg(2)=1. &lt;br/&gt;
&lt;/em&gt;&lt;em&gt;⇒ N obj, M unions will take (almost) linear time&lt;/em&gt;*  &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image015.png"/&gt; &lt;br/&gt;
(有人证明了不存在&lt;em&gt;理论上&lt;/em&gt;linear的算法. )&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;conclusion&lt;/strong&gt;: both UNION and FIND will be in &lt;strong&gt;constant time&lt;/strong&gt;.&lt;/p&gt;
&lt;h2 id="summery_1"&gt;summery&lt;/h2&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image017.png"/&gt; &lt;br/&gt;
上面这个表格好像quick union的部分有问题? 最坏情况下应该是N+MN吧??&lt;br/&gt;
书上是这么写的:  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image016.png"/&gt;&lt;/p&gt;
&lt;p&gt;WQUCF reduce 30 years to 6 seconds. &lt;/p&gt;
&lt;h1 id="5-union-find-application_1"&gt;5. Union Find Application&lt;/h1&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image018.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;percolation&lt;/li&gt;
&lt;li&gt;dynamic connectivity&lt;/li&gt;
&lt;li&gt;Kruskal MST algo&lt;/li&gt;
&lt;li&gt;Games (GO)&lt;/li&gt;
&lt;li&gt;.......&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id="percolation"&gt;percolation&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;model: &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;N&lt;em&gt;N grid of sites&lt;br/&gt;
⇒ each site is open with proba=&lt;/em&gt;p&lt;em&gt;&lt;br/&gt;
⇒ sys &lt;/em&gt;&lt;em&gt;percolate&lt;/em&gt;* iff bottom and top are connected by open sites.  &lt;br/&gt;
&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image019.png"/&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;question: the &lt;em&gt;percolation probability&lt;/em&gt; as a function of &lt;em&gt;p &lt;/em&gt;(&lt;strong&gt;phase transition&lt;/strong&gt;)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image020.png"/&gt; &lt;br/&gt;
nobody knows how to get the threshold mathematically&lt;br/&gt;
⇒ run &lt;em&gt;simulations&lt;/em&gt; to find out the phase transition &lt;em&gt;threshold&lt;/em&gt;.   &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Monte Carlo simulation   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;→ all sites initilized to be &lt;em&gt;closed&lt;/em&gt;&lt;br/&gt;
→ randomly open sites &lt;em&gt;one by one&lt;/em&gt; &lt;br/&gt;
→ when the sys percolates, the &lt;em&gt;vacancy percentage&lt;/em&gt; is an estimate of &lt;em&gt;p&lt;/em&gt; &lt;br/&gt;
*(run above simulation for millions of times)   &lt;/p&gt;
&lt;h3 id="implementation_3"&gt;implementation&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;N^2 sites, named 0 to N^2-1  &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image022.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;add 2 more vertual sites: one on top, one on bottom   &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/algoI_week1_1/pasted_image021.png"/&gt; &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;openning a site: union to adjcent open sites (at most 4 unions)&lt;/li&gt;
&lt;/ul&gt;</content><category term="notes"/><category term="algorithm"/></entry><entry><title>运筹的力量: 用线性规划解决Google 2014 HashCode问题</title><link href="https://x-wei.github.io/tech/hashcode2014-solved-by-LP.html" rel="alternate"/><published>2015-02-02T00:00:00+01:00</published><updated>2015-02-02T00:00:00+01:00</updated><author><name>mx</name></author><id>tag:x-wei.github.io,2015-02-02:/tech/hashcode2014-solved-by-LP.html</id><summary type="html">&lt;p&gt;INF580(programmation par contraintes) 大概是在X学到的最有用的一门课, 它让我能够用把运筹学(MAP557)里学到的东西和计算机结合起来: 用电脑的力量解决(大规模)运筹问题. &lt;/p&gt;
&lt;p&gt;这 …&lt;/p&gt;</summary><content type="html">&lt;p&gt;INF580(programmation par contraintes) 大概是在X学到的最有用的一门课, 它让我能够用把运筹学(MAP557)里学到的东西和计算机结合起来: 用电脑的力量解决(大规模)运筹问题. &lt;/p&gt;
&lt;p&gt;这门课的projet是去年巴黎谷歌举行的一个比赛的题目: 最优化谷歌街景拍照小车的路线. 做这个projet的三周里, 我和Manu从一开始信心满满, 到中间一筹莫展, 再到后来柳暗花明, 以及最后乘胜追击终于在今晚得到了近乎完美的解答, 非常精彩, 这里特意一记.&lt;/p&gt;
&lt;h1 id="_1"&gt;问题描述&lt;/h1&gt;
&lt;p&gt;谷歌那次比赛的题目在这里(我们做的是Main Round的题目): &lt;a href="https://sites.google.com/site/hashcode2014/tasks"&gt;https://sites.google.com/site/hashcode2014/tasks&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;简单来说, 就是已知巴黎的道路信息, 设法用八辆车(每辆车的行驶时间有限)从巴黎谷歌出发, 尽可能多的走遍巴黎的所有街道, 参赛者给出这些车的路线, 他们的分数就是这八辆车走过的街道的长度之和(重复走的街道不算分). &lt;/p&gt;
&lt;p&gt;去年四月份我们也参加了这个比赛, 不过当时纠结于如何设计每辆车的路线, 最后只是用了贪心算法, 再加上一点点的随机, 得到的结果并不好... 当时ENS的人包揽了前三名, 而且比赛后进一步把分数刷到了满分: 他们的路线可以把所有街道都跑遍. &lt;/p&gt;
&lt;p&gt;这学期学了INF580以后, 手里有了&lt;strong&gt;JaCoP&lt;/strong&gt;以及&lt;strong&gt;AMPL&lt;/strong&gt;等"重型武器", 我们经过一番努力也得到了满分, 而且用了几乎最少的时间. 代码放在了: &lt;a href="https://github.com/X-Wei/INF580_HashCode2014"&gt;https://github.com/X-Wei/INF580_HashCode2014&lt;/a&gt; (里面还有个pdf的报告, 比这篇博客里说的精炼).&lt;/p&gt;
&lt;h1 id="i"&gt;I. 初步建模&lt;/h1&gt;
&lt;h2 id="lp"&gt;线性规划(LP)模型&lt;/h2&gt;
&lt;p&gt;站在一个更高的角度上考虑这个问题, 从一个线性规划的角度看, 给定一个图&lt;code&gt;G(V,E)&lt;/code&gt;, 目标是最大化走过的街道长度, 如果用对每条街道&lt;code&gt;e&lt;/code&gt;, 定义一个&lt;code&gt;x_e&lt;/code&gt;,: 当一条街被经过的时候使它为1, 否则为0, 那么目标函数就是一个x的线性组合(系数就是对应街道的长度). &lt;/p&gt;
&lt;p&gt;但是如果一条街被经过了大于一次, &lt;code&gt;x_e&lt;/code&gt;也只能是1, 所以再引入一个变量&lt;code&gt;y_e&lt;/code&gt;: 用来表示一条街被经过的&lt;strong&gt;次数&lt;/strong&gt;. 所以&lt;code&gt;x_e&lt;/code&gt;可以看成是&lt;code&gt;y_e&lt;/code&gt;的indicatrice函数: &lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/equation.png"/&gt;, 这一点可以通过增加线性约束: &lt;code&gt;x_e&amp;lt;=y_e&lt;/code&gt; 即可实现, 因为&lt;code&gt;x_e&lt;/code&gt;的取值范围是{0,1}. &lt;/p&gt;
&lt;p&gt;不过一条街可能从两个方向被经过(&lt;code&gt;G&lt;/code&gt;里面的边是有向的), 如果&lt;code&gt;e&lt;/code&gt;'代表反方向的&lt;code&gt;e&lt;/code&gt;, 那么还应该增加约束:  &lt;code&gt;x_e+x_e'&amp;lt;=1&lt;/code&gt; 就好了. &lt;/p&gt;
&lt;p&gt;接下来&lt;code&gt;y&lt;/code&gt;要满足的就是所有的&lt;code&gt;y&lt;/code&gt;要组成一个&lt;em&gt;路径(path)&lt;/em&gt;, 对于既不是起点又不是终点的一个节点&lt;code&gt;v&lt;/code&gt;, 还是很好写的, 类似flot: &lt;code&gt;sum(进入v的y_e) = sum(从v流出的y_e)&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;对于起点&lt;code&gt;v_start&lt;/code&gt;来说, 其实也不难: &lt;code&gt;sum(进入v_start的y_e) = sum(从v-start流出的y_e)+1&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;但是对于终点的话, 有个问题是我们不知道车会停在哪里! Manu太聪明了, 对每一个节点&lt;code&gt;v&lt;/code&gt;引入了另一个变量&lt;code&gt;f_v&lt;/code&gt;,取值范围也是{0,1}, 如果在节点&lt;code&gt;v&lt;/code&gt;停下来, 那么&lt;code&gt;f_v&lt;/code&gt;等于1, 否则就是0. 所以上面的约束可以写成: &lt;code&gt;sum(进入v的y) = sum(从v流出的y_e)+f_v&lt;/code&gt;. 另外别忘了只能停在一个节点, 所以再加约束: &lt;code&gt;sum(所有的f_v)=1&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;以上的目标函数以及约束, 虽然数目庞大, 但是都是线性的, 所以是一个整数线性规划问题, 写成数学形式就是: &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/pasted_image001.png"/&gt;&lt;/p&gt;
&lt;h2 id="solution"&gt;从solution得到路径&lt;/h2&gt;
&lt;p&gt;一旦上面那个线性规划问题解决了, 我们得到的将会是那些变量&lt;code&gt;x&lt;/code&gt;,&lt;code&gt;y&lt;/code&gt;,以及&lt;code&gt;f&lt;/code&gt;, 但是需要从中提取一条路径最后才能作为solution!! &lt;/p&gt;
&lt;p&gt;这个问题实际上可以归结为: 给定一个一笔画的曲线(其实就是那些&lt;code&gt;y&lt;/code&gt;: 可以想象把每条边都复制&lt;code&gt;y&lt;/code&gt;次, 得到的就是这么一个曲线了), 找出一个可以将其一笔画出来的路径(这条路径也叫"欧拉路径", 没"汉密尔顿路径"有名). 聪明的Manu很快想出来一个算法(我们叫它"Orsini算法"): 大意是当走到底没有走完的时候, 把那些错过的路径夹在原路径的中间就好了. &lt;/p&gt;
&lt;p&gt;算法描述如下: &lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;i) 从起点开始出发走, 把走过的边涂上颜色(以后不能再走), 只要还可以继续走(还有没有着色的边可走)就一直走下去, 一直到无路可走. (应该会停在&lt;code&gt;f=1&lt;/code&gt;的地方), 得到路径&lt;code&gt;p0&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;ii)  如果所有边已经被走过了: &lt;strong&gt;over&lt;/strong&gt;. 如果没有: 找一个没有走过的边与&lt;code&gt;p0&lt;/code&gt;的交叉点: &lt;code&gt;v&lt;/code&gt;(如果找不到的话说明有问题: 后面就遇到这个问题了), 然后执行(iii)&lt;/p&gt;
&lt;p&gt;iii) 从&lt;code&gt;v&lt;/code&gt;出发, 在进行类似(i)的操作得到一条路径(应该是一个环), 然后把&lt;code&gt;p0&lt;/code&gt;从&lt;code&gt;v&lt;/code&gt;那里劈开, 把这个环塞到中间组成新的&lt;code&gt;p0&lt;/code&gt;, 然后再执行(ii).  &lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;这样就可以得到对应的路径了. &lt;/p&gt;
&lt;h2 id="_2"&gt;一开始的想法&lt;/h2&gt;
&lt;p&gt;以上的建模是针对一辆车的, 我们一开始的想法是: 对一辆车进行这个操作, 得到结果以后更新一下&lt;code&gt;G&lt;/code&gt;(把那些已经走过的街道的长度设为0, 然后再走下一辆车... 这样跑8次就能得到最优解了. &lt;/p&gt;
&lt;p&gt;一切看起来&lt;em&gt;似乎&lt;/em&gt;都非常完美......&lt;/p&gt;
&lt;h1 id="ii_1"&gt;II.遇到的问题&lt;/h1&gt;
&lt;h2 id="_3"&gt;计算能力问题&lt;/h2&gt;
&lt;p&gt;写好了AMPL的程序以后, 我们遇到的第一个问题是: 这么大的问题, 一般电脑算不出来(曾经用glpk让电脑跑了一夜, 还是没有得到结果). &lt;/p&gt;
&lt;p&gt;后来问老师, 老师说glpk并不是非常高效的求解器, 然后推荐给了我们一个非常给力的网站: &lt;a href="http://neos-server.org/neos/"&gt;NEOS&lt;/a&gt; ! 这个网站可以让人上传AMPL程序, 然后用它们的服务器跑, 而且使用的求解器也是商用的, 比开源求解器快的不是一个数量级(我们发现最快的求解器是&lt;em&gt;Gurobi&lt;/em&gt;, 十分给力). &lt;/p&gt;
&lt;p&gt;这样一来计算的问题就解决了, 但是我们很快发现一个更严重的问题, 是我们的建模里的一个严重缺陷...&lt;/p&gt;
&lt;h2 id="subtour"&gt;subtour问题&lt;/h2&gt;
&lt;p&gt;我们兴冲冲的拿NEOS的结果跑Orsini算法的时候, 发现总是报错: 也就是在第二步, 程序无法找到一个和&lt;code&gt;p0&lt;/code&gt;有交叉点的边: &lt;em&gt;也就意味着我们的模型得到的路径并不是只有一个connected component!!! &lt;/em&gt;也就是说, 我们得到的解其实是一条从起点到某个终点的路径, 外加很多和这个路径没有交点的圈圈(subtour)!&lt;/p&gt;
&lt;p&gt;是啊, 这个问题很类似旅行商问题(TSP), 而TSP的困难之一 就是要解决subtour的话需要加入2^n个新的约束.... 2^10000个约束? impossible...&lt;/p&gt;
&lt;h1 id="iii-subtour_1"&gt;III. subtour问题的"解决"&lt;/h1&gt;
&lt;h2 id="_4"&gt;各种纠结&lt;/h2&gt;
&lt;p&gt;在一次PC上有一道题目介绍了TSP subtour问题的一种建模方式, "potentiel"建模, 可以防止加入2^n个约束: 为每个节点&lt;code&gt;v&lt;/code&gt;引入新的变量&lt;code&gt;u_v&lt;/code&gt;,&lt;code&gt;u_v&lt;/code&gt;代表了节点&lt;code&gt;v&lt;/code&gt;被访问的顺序, 约束做的非常巧妙, 是这样的: &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/pasted_image002.png"/&gt;&lt;/p&gt;
&lt;p&gt;这样, 当&lt;code&gt;x_ij&lt;/code&gt;是1的时候, 就保证&lt;code&gt;u_j&lt;/code&gt;比&lt;code&gt;u_i&lt;/code&gt;大1, 而当&lt;code&gt;x_ij&lt;/code&gt;是0的时候, 这个约束则非常松弛, 几乎相当于没有. &lt;/p&gt;
&lt;p&gt;不过这个方法套到我们这个projet的话也有问题: 那就是每个节点只能有一个&lt;code&gt;u_v&lt;/code&gt;, 所以每个节点只能最多访问一次.... 不过我们很快想到了办法: 把所有节点复制一个(复制"一层"), 然后每条边的话也进行复制, 同时加上那些连接各层的边. &lt;/p&gt;
&lt;p&gt;举个例子, 原来的一条边是: &lt;code&gt;(u, v)&lt;/code&gt;, 我们复制了一层, 这些新节点叫它们&lt;code&gt;u',v&lt;/code&gt;',... 那么在这个两层的图里, 我们要把原来的这条边变成4条: &lt;code&gt;(u, v)&lt;/code&gt;, &lt;code&gt;(u, v')&lt;/code&gt;, &lt;code&gt;(u', v)&lt;/code&gt; 和 &lt;code&gt;(u', v')&lt;/code&gt;. 这样就可以保证路径可以经过一个点两次了, 如果想要保证可以经过一个点K次, 只要做K层就好了(每条边变成K^2条). &lt;/p&gt;
&lt;p&gt;然后, &lt;code&gt;x&lt;/code&gt;也不需要了, 因为每条边的&lt;code&gt;y&lt;/code&gt;最大就是1. 但是还有一个问题是目标函数, 由于一条边变成了四条, 如果走四遍的话就多算了四次这条边的长度... 有两种解决办法: 一是类似前面的方法, 给每条边指定定一个indicatrice, 这样就不会重复了, 还有一种更简单的办法是, 在四条边里, 只取一条边的长度保持不变, 其他长度都设成0, 算法自然会优先走那条长度不是0的边(这个没有仔细证明, 不过貌似是这样的). 我们采用了第二个办法.... &lt;/p&gt;
&lt;p&gt;就这样废了好大功夫, 写好了两层节点的程序, 送去NEOS一跑.... 超时了(超过8h后NEOS会自动停止求解过程)... 后来我们发现即使是不多加新一层的程序, 也会超时. 那节PC里也说, 这种建模方法实际上计算效率比加入2^N个约束的建模还要差... &lt;/p&gt;
&lt;p&gt;所以总结一下就是: 问题还是没有解决...&lt;/p&gt;
&lt;h2 id="subtour_1"&gt;绕过subtour问题&lt;/h2&gt;
&lt;p&gt;就在一筹莫展之际, Manu提议把搜索的范围缩小: 不用整个巴黎的数据, 只取起点附近的区域, 这样的话, 说不定我们原先的模型得到的结果会少一点connected components... 试了一下, 果然! 虽然没有强制要求路径的连通性, 得到的结果确实(几乎)只有一个联通分支! &lt;/p&gt;
&lt;p&gt;后来就想到了一个很聪明的办法: 用八倍的T作为时间限制, 让一辆车去跑, 由于时间很充分, 我们得到的解应该不太会出现多个联通分支, 然后一旦得到了这个路径(后来我们叫它"big path"), 只需要把它分成8段, 每辆车先从起点(巴黎谷歌)跑到每一段的开头, 然后沿着这条路跑就好了啊!! 虽然从巴黎谷歌跑到每一段的起点会稍微浪费一些时间, 但是这点损失其实微不足道!! 而且也不用跑8次LP这么麻烦了 -- 要是早点想到这个就好了!!&lt;/p&gt;
&lt;p&gt;而且很神奇的是, 把时间变成了8T以后, 我们的Lp模型计算的更快了: 原先要计算30分钟左右, 现在只要差不多3分钟就出结果了!! 这一点没太想明白, 可能是搜索的空间变小了??&lt;/p&gt;
&lt;p&gt;说写就写, 最短路径用Dijkstra算法就能得到了, 不一会就写出了这个把一条big path变成8条small path的程序. 然后我们一举得到了1957596分(离满分还差了两千米左右)!!&lt;/p&gt;
&lt;h1 id="iv_1"&gt;IV. 进一步优化&lt;/h1&gt;
&lt;p&gt;优化的话有两个方向: 第一个方向是修改那个程序代码, 使得每次走到big path某段起点的时候可以少走些路, 不过这个方向应该没什么前途: 程序写起来麻烦不说, 可以改进的空间也很有限, 因为big path一共也没有剩多少时间, 所以八辆车是不可能把big path走完的. 第二个方向则是设法优化big path的时间使用, 使得它在得到最长路径的同时使用尽量少的时间. &lt;/p&gt;
&lt;h2 id="_5"&gt;引入时间正则项&lt;/h2&gt;
&lt;p&gt;其实8T作为时间来说非常充裕, 但是我们的解里面, big path还是把时间用的差不多了: 因为时间根本没有出现在目标函数里. 所以, 可以把时间也作为目标函数加上去, 不过要注意最优先要优化的还是路径长度, 所以时间项前面要乘以一个非常小的数(比如0.000001), 类似做regularization. &lt;/p&gt;
&lt;p&gt;所以新的目标函数是: &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/pasted_image003.png"/&gt;&lt;/p&gt;
&lt;p&gt;这样一运行, 我们的big path居然剩下了六千多秒的时间!!! 这些时间足够八辆车跑到各段的起点了!! 我们这样, 八辆车走完了big path所有的路程得到的结果离满分只差了7米, 而最后一辆车还有两千多秒没有走! &lt;/p&gt;
&lt;p&gt;检查了一下, 发现有一个7米长的路是唯一剩下没走过的路: 于是只要再让最后一辆车去走一下就好了(因为时间够用), 最终我们的方案走完了整个巴黎:&lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/pasted_image005.png"/&gt;&lt;/p&gt;
&lt;p&gt;等一下, 这里有点奇怪: 为什么优化得到的结果并不是最优的(没有走完所有的路程)? 我们通过后来手动走那条剩下的路都没有超时, 所以说其实肯定可以在8T的时间走遍所有街道的! 后来查了一下才发现, 原来Gurobi并不是返回最优解, 而是当当前可行解与最优解足够接近的时候就直接停止, 这个参数的名字叫mipgap, 更多参数可以参考这里: &lt;a href="http://www.gurobi.com/documentation/6.0/ampl-gurobi-guide/parameters"&gt;http://www.gurobi.com/documentation/6.0/ampl-gurobi-guide/parameters&lt;/a&gt; .&lt;/p&gt;
&lt;p&gt;这也就解释了为什么NEOS得到的解不是最优的, 不过还好, 通过最后手动添加那条没走的边, 还是走完了所有的街道. &lt;/p&gt;
&lt;p&gt;............&lt;/p&gt;
&lt;p&gt;只是作为强迫症的话觉得还是有点......不够完美.&lt;/p&gt;
&lt;h2 id="_6"&gt;直接优化时间&lt;/h2&gt;
&lt;p&gt;今晚, 机智的Manu想到了解决办法: 既然知道所有的街道都会被走遍, 直接不把它看成目标, 而是直接作为约束好了, 然后约束直接改成优化时间! &lt;/p&gt;
&lt;p&gt;要就经过所有街道的约束很简单, 那就是对任何街道&lt;code&gt;e&lt;/code&gt;, 都有: &lt;code&gt;y_e+y_e'&amp;gt;=1&lt;/code&gt;. 另外肯定所有街道都会经过, &lt;code&gt;x&lt;/code&gt;就没有必要存在了. &lt;/p&gt;
&lt;p&gt;LP模型表达为: &lt;/p&gt;
&lt;p&gt;&lt;img alt="" class="img-responsive" src="../images/./运筹的力量_用LP解决Google_2014_Hashcode/pasted_image004.png"/&gt;&lt;/p&gt;
&lt;p&gt;用这样的模型, 我们的big path 省下了一万两千多秒, 所以我们的最终结果里, 最后的一辆车跑完以后还有9596秒没有用!!&lt;/p&gt;
&lt;p&gt;到这一步, 真的可以算是完美解决这个问题了, 而且强迫症也得救了. &lt;/p&gt;
&lt;p&gt;Yeah!  : )&lt;/p&gt;</content><category term="tech"/><category term="LP"/><category term="algorithm"/></entry></feed>