salt fish on the moonhttps://www.git.moe/2020-04-25T00:00:00+08:00cin vs getline vs cin.getline2020-04-25T00:00:00+08:002020-04-25T00:00:00+08:00fx-moontag:www.git.moe,2020-04-25:/cin-vs-getline-vs-cingetline.html<h1>cin vs getline vs cin.getline</h1>
<h2>Case with <code>'\n'</code></h2>
<h3>cin</h3>
<div class="highlight"><pre><span></span><span class="k">drop</span> <span class="k">all</span> <span class="o">`</span><span class="s1">'\n'</span><span class="o">`</span> <span class="k">except</span> <span class="k">last</span> <span class="n">one</span> <span class="p">(</span><span class="n">just</span> <span class="n">leave</span> <span class="n">it</span> <span class="k">in</span> <span class="n">the</span> <span class="n">buffer</span><span class="p">,</span><span class="n">won</span><span class="err">'</span><span class="n">t</span> <span class="k">get</span> <span class="n">it</span> <span class="k">and</span> <span class="n">will</span> <span class="n">finally</span> <span class="k">drop</span> <span class="n">it</span><span class="p">).</span>
</pre></div>
<h3>getline</h3>
<div class="highlight"><pre><span></span><span class="nv">read</span> <span class="k">until</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">and</span> <span class="nv">replace</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">with</span> `<span class="s1">'</span><span class="s">\0</span><span class="s1">'</span>`.
</pre></div>
<h3>cin.getline</h3>
<div class="highlight"><pre><span></span><span class="nv">same</span> <span class="nv">with</span> <span class="nv">getline</span>, <span class="nv">replace</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">with</span> `<span class="s1">'</span><span class="s">\0</span><span class="s1">'</span>`.
<span class="nv">but …</span></pre></div><h1>cin vs getline vs cin.getline</h1>
<h2>Case with <code>'\n'</code></h2>
<h3>cin</h3>
<div class="highlight"><pre><span></span><span class="k">drop</span> <span class="k">all</span> <span class="o">`</span><span class="s1">'\n'</span><span class="o">`</span> <span class="k">except</span> <span class="k">last</span> <span class="n">one</span> <span class="p">(</span><span class="n">just</span> <span class="n">leave</span> <span class="n">it</span> <span class="k">in</span> <span class="n">the</span> <span class="n">buffer</span><span class="p">,</span><span class="n">won</span><span class="err">'</span><span class="n">t</span> <span class="k">get</span> <span class="n">it</span> <span class="k">and</span> <span class="n">will</span> <span class="n">finally</span> <span class="k">drop</span> <span class="n">it</span><span class="p">).</span>
</pre></div>
<h3>getline</h3>
<div class="highlight"><pre><span></span><span class="nv">read</span> <span class="k">until</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">and</span> <span class="nv">replace</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">with</span> `<span class="s1">'</span><span class="s">\0</span><span class="s1">'</span>`.
</pre></div>
<h3>cin.getline</h3>
<div class="highlight"><pre><span></span><span class="nv">same</span> <span class="nv">with</span> <span class="nv">getline</span>, <span class="nv">replace</span> `<span class="s1">'</span><span class="se">\n</span><span class="s1">'</span>` <span class="nv">with</span> `<span class="s1">'</span><span class="s">\0</span><span class="s1">'</span>`.
<span class="nv">but</span> <span class="nv">used</span> <span class="k">for</span> <span class="nv">c_string</span>.
</pre></div>config git2020-03-07T00:00:00+08:002020-03-07T00:00:00+08:00fx-moontag:www.git.moe,2020-03-07:/config-git.html<p>Git saves your <em>system config</em> in <code>/etc/gitconfig</code> , <em>user config</em> in <code>~/.gitconfig</code> or <code>~/.config/git/config</code> and <em>repository config</em> in <code>.git/config</code></p>
<p>Each config will override the previous one so the <strong>repository config</strong> will override the other config</p>
<p>Config your username and email:</p>
<div class="highlight"><pre><span></span>$ git config --global user.name <span class="s2">"fx-moon"</span>
$ git …</pre></div><p>Git saves your <em>system config</em> in <code>/etc/gitconfig</code> , <em>user config</em> in <code>~/.gitconfig</code> or <code>~/.config/git/config</code> and <em>repository config</em> in <code>.git/config</code></p>
<p>Each config will override the previous one so the <strong>repository config</strong> will override the other config</p>
<p>Config your username and email:</p>
<div class="highlight"><pre><span></span>$ git config --global user.name <span class="s2">"fx-moon"</span>
$ git config --global user.email fx-moon@outlook.com
</pre></div>
<blockquote>
<p>To get all the config you can use <code>man git-config</code> or <a href="http://git-scm.com/docs/git-config.html">http://git-scm.com/docs/git-config.html</a> .</p>
</blockquote>strlen_analyze2019-04-01T00:00:00+08:002019-04-01T00:00:00+08:00fx-moontag:www.git.moe,2019-04-01:/strlen_analyze.html<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><vector></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><string></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><stack></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><ctime></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><windows.h></span><span class="cp"></span>
<span class="k">const</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="mi">1024</span><span class="o">*</span><span class="mi">1024</span><span class="o">*</span><span class="mi">500</span><span class="p">;</span>
<span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span>
<span class="k">class</span> <span class="nc">timer</span>
<span class="p">{</span>
<span class="kt">long</span> <span class="kt">long</span> <span class="n">t</span><span class="p">;</span>
<span class="k">public</span><span class="o">:</span>
<span class="n">timer</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">t</span> <span class="o">=</span> <span class="n">clock</span><span class="p">();</span>
<span class="p">}</span>
<span class="o">~</span><span class="n">timer</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">cout</span> <span class="o"><<</span> <span class="n">clock</span><span class="p">()</span> <span class="o">-</span> <span class="n">t</span> <span class="o"><<</span> <span class="n">endl</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">};</span>
<span class="kt">size_t</span> <span class="nf">strlen1</span><span class="p">(</span><span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">str</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">register</span> <span class="kt">int</span> <span class="n">length</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
<span class="k">while</span> <span class="p">(</span><span class="o">*</span><span class="n">str</span><span class="o">++</span><span class="p">)</span>
<span class="o">++</span><span class="n">length</span><span class="p">;</span>
<span class="k">return</span> <span class="p">(</span><span class="n">length …</span></pre></div><div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><vector></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><string></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><stack></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><ctime></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><windows.h></span><span class="cp"></span>
<span class="k">const</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="mi">1024</span><span class="o">*</span><span class="mi">1024</span><span class="o">*</span><span class="mi">500</span><span class="p">;</span>
<span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span>
<span class="k">class</span> <span class="nc">timer</span>
<span class="p">{</span>
<span class="kt">long</span> <span class="kt">long</span> <span class="n">t</span><span class="p">;</span>
<span class="k">public</span><span class="o">:</span>
<span class="n">timer</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">t</span> <span class="o">=</span> <span class="n">clock</span><span class="p">();</span>
<span class="p">}</span>
<span class="o">~</span><span class="n">timer</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">cout</span> <span class="o"><<</span> <span class="n">clock</span><span class="p">()</span> <span class="o">-</span> <span class="n">t</span> <span class="o"><<</span> <span class="n">endl</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">};</span>
<span class="kt">size_t</span> <span class="nf">strlen1</span><span class="p">(</span><span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">str</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">register</span> <span class="kt">int</span> <span class="n">length</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
<span class="k">while</span> <span class="p">(</span><span class="o">*</span><span class="n">str</span><span class="o">++</span><span class="p">)</span>
<span class="o">++</span><span class="n">length</span><span class="p">;</span>
<span class="k">return</span> <span class="p">(</span><span class="n">length</span><span class="p">);</span>
<span class="p">}</span>
<span class="kt">size_t</span> <span class="nf">strlen3</span><span class="p">(</span><span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">sstr</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">register</span> <span class="kt">int</span> <span class="n">length</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
<span class="kt">int</span> <span class="n">size</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
<span class="kt">int</span> <span class="o">*</span><span class="n">p_size</span> <span class="o">=</span> <span class="o">&</span><span class="n">size</span><span class="p">;</span>
<span class="kr">__asm</span><span class="p">{</span>
<span class="n">mov</span> <span class="n">edi</span><span class="p">,</span><span class="n">sstr</span><span class="p">;</span>
<span class="n">mov</span> <span class="n">ecx</span><span class="p">,</span><span class="mh">0xffffffff</span><span class="p">;</span>
<span class="n">xor</span> <span class="n">eax</span><span class="p">,</span><span class="n">eax</span><span class="p">;</span>
<span class="n">repne</span> <span class="n">scasb</span><span class="p">;</span>
<span class="n">mov</span> <span class="n">eax</span><span class="p">,</span><span class="n">dword</span> <span class="n">ptr</span> <span class="p">[</span><span class="n">p_size</span><span class="p">];</span>
<span class="n">mov</span> <span class="n">dword</span> <span class="n">ptr</span><span class="p">[</span><span class="n">eax</span><span class="p">],</span><span class="n">ecx</span><span class="p">;</span>
<span class="p">}</span>
<span class="k">return</span> <span class="mh">0xffffffff</span> <span class="o">-</span> <span class="n">size</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span>
<span class="p">}</span>
<span class="kt">size_t</span> <span class="nf">strlen2</span><span class="p">(</span><span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">str</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">char_ptr</span> <span class="o">=</span> <span class="nb">NULL</span><span class="p">;</span>
<span class="k">const</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">int</span> <span class="o">*</span><span class="n">longword_ptr</span> <span class="o">=</span> <span class="nb">NULL</span><span class="p">;</span>
<span class="k">register</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">int</span> <span class="n">longword</span><span class="p">,</span> <span class="n">magic_bits</span><span class="p">;</span>
<span class="k">for</span> <span class="p">(</span><span class="n">char_ptr</span> <span class="o">=</span> <span class="n">str</span><span class="p">;</span> <span class="p">((</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">int</span><span class="p">)(</span><span class="n">char_ptr</span><span class="p">)</span>
<span class="o">&</span> <span class="p">(</span><span class="k">sizeof</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">int</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">))</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">;</span>
<span class="o">++</span><span class="n">char_ptr</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">if</span> <span class="p">(</span><span class="o">*</span><span class="n">char_ptr</span> <span class="o">==</span> <span class="sc">'\0'</span><span class="p">)</span>
<span class="k">return</span> <span class="n">char_ptr</span> <span class="o">-</span> <span class="n">str</span><span class="p">;</span>
<span class="p">}</span>
<span class="n">longword_ptr</span> <span class="o">=</span> <span class="p">(</span><span class="k">const</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">int</span> <span class="o">*</span><span class="p">)</span><span class="n">char_ptr</span><span class="p">;</span>
<span class="n">magic_bits</span> <span class="o">=</span> <span class="mh">0x7efefeffL</span><span class="p">;</span>
<span class="k">for</span> <span class="p">(;;)</span>
<span class="p">{</span>
<span class="n">longword</span> <span class="o">=</span> <span class="o">*</span><span class="n">longword_ptr</span><span class="o">++</span><span class="p">;</span>
<span class="k">if</span> <span class="p">((((</span><span class="n">longword</span> <span class="o">+</span> <span class="n">magic_bits</span><span class="p">)</span> <span class="o">^</span> <span class="o">~</span><span class="n">longword</span><span class="p">)</span> <span class="o">&</span> <span class="o">~</span><span class="n">magic_bits</span><span class="p">)</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span>
<span class="p">{</span>
<span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="n">cp</span> <span class="o">=</span> <span class="p">(</span><span class="k">const</span> <span class="kt">char</span> <span class="o">*</span><span class="p">)(</span><span class="n">longword_ptr</span> <span class="o">-</span> <span class="mi">1</span><span class="p">);</span>
<span class="k">if</span> <span class="p">(</span><span class="n">cp</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="sc">'\0'</span><span class="p">)</span>
<span class="k">return</span> <span class="n">cp</span> <span class="o">-</span> <span class="n">str</span><span class="p">;</span>
<span class="k">if</span> <span class="p">(</span><span class="n">cp</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="sc">'\0'</span><span class="p">)</span>
<span class="k">return</span> <span class="n">cp</span> <span class="o">-</span> <span class="n">str</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span>
<span class="k">if</span> <span class="p">(</span><span class="n">cp</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span> <span class="o">==</span> <span class="sc">'\0'</span><span class="p">)</span>
<span class="k">return</span> <span class="n">cp</span> <span class="o">-</span> <span class="n">str</span> <span class="o">+</span> <span class="mi">2</span><span class="p">;</span>
<span class="k">if</span> <span class="p">(</span><span class="n">cp</span><span class="p">[</span><span class="mi">3</span><span class="p">]</span> <span class="o">==</span> <span class="sc">'\0'</span><span class="p">)</span>
<span class="k">return</span> <span class="n">cp</span> <span class="o">-</span> <span class="n">str</span> <span class="o">+</span> <span class="mi">3</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">}</span>
<span class="p">}</span>
<span class="kt">char</span> <span class="n">s</span><span class="p">[</span><span class="n">n</span><span class="p">]{</span><span class="mi">0</span><span class="p">};</span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o"><</span> <span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span>
<span class="n">s</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="sc">'A'</span><span class="p">;</span>
<span class="p">{</span>
<span class="n">timer</span> <span class="n">t</span><span class="p">;</span>
<span class="n">cout</span><span class="o"><<</span><span class="n">strlen</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o"><<</span><span class="sc">' '</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">{</span>
<span class="n">timer</span> <span class="n">t</span><span class="p">;</span>
<span class="n">cout</span><span class="o"><<</span><span class="n">strlen1</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o"><<</span><span class="sc">' '</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">{</span>
<span class="n">timer</span> <span class="n">t</span><span class="p">;</span>
<span class="n">cout</span><span class="o"><<</span><span class="n">strlen2</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o"><<</span><span class="sc">' '</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">{</span>
<span class="n">timer</span> <span class="n">t</span><span class="p">;</span>
<span class="n">cout</span><span class="o"><<</span><span class="n">strlen3</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o"><<</span><span class="sc">' '</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">{</span>
<span class="n">timer</span> <span class="n">t</span><span class="p">;</span>
<span class="n">Sleep</span><span class="p">(</span><span class="mi">1000</span><span class="p">);</span>
<span class="p">}</span>
<span class="n">system</span><span class="p">(</span><span class="s">"pause"</span><span class="p">);</span>
<span class="k">return</span> <span class="mi">0</span><span class="p">;</span>
<span class="p">}</span>
</pre></div>Very Simple Powershell2019-01-22T00:00:00+08:002019-01-22T00:00:00+08:00fx-moontag:www.git.moe,2019-01-22:/very-simple-powershell.html<h1>Basic Powershell</h1>
<h2>Variable</h2>
<p><code>$<name>=<value></code></p>
<div class="highlight"><pre><span></span><span class="err">$</span><span class="n">usrname</span><span class="o">=</span><span class="s1">'John'</span>
<span class="err">$</span><span class="n">len</span><span class="o">=</span><span class="mi">32</span>
</pre></div>
<blockquote>
<p>$null -> null value</p>
<p>$true -> boolean true</p>
<p>$false -> boolean false</p>
<p>$_ -> the variable currently being processed</p>
</blockquote>
<h2>Data Structure</h2>
<h3>Array</h3>
<div class="highlight"><pre><span></span><span class="nv">$var</span><span class="p">=@(<</span><span class="n">element</span><span class="p">>,<</span><span class="n">element</span><span class="p">>,...)</span>
<span class="nv">$var</span><span class="p">[</span><span class="n">0</span><span class="p">]</span>
<span class="nv">$var</span><span class="p">[</span><span class="n">100</span><span class="p">]=</span><span class="n">2333</span>
</pre></div>
<h3>Hash Table</h3>
<div class="highlight"><pre><span></span><span class="nv">$var</span><span class="p">=@{<</span><span class="n">key</span><span class="p">>=<</span><span class="n">value</span><span class="p">>,...}</span>
<span class="nv">$var</span><span class="p">[<</span><span class="n">key</span><span class="p">>]</span>
<span class="nv">$var</span><span class="p">.</span><span class="n">key</span>
</pre></div>
<h2>Process Control</h2>
<h3>Branch</h3>
<div class="highlight"><pre><span></span><span class="k">if</span><span class="p">()</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">elseif</span><span class="p">()</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">else …</span></pre></div><h1>Basic Powershell</h1>
<h2>Variable</h2>
<p><code>$<name>=<value></code></p>
<div class="highlight"><pre><span></span><span class="err">$</span><span class="n">usrname</span><span class="o">=</span><span class="s1">'John'</span>
<span class="err">$</span><span class="n">len</span><span class="o">=</span><span class="mi">32</span>
</pre></div>
<blockquote>
<p>$null -> null value</p>
<p>$true -> boolean true</p>
<p>$false -> boolean false</p>
<p>$_ -> the variable currently being processed</p>
</blockquote>
<h2>Data Structure</h2>
<h3>Array</h3>
<div class="highlight"><pre><span></span><span class="nv">$var</span><span class="p">=@(<</span><span class="n">element</span><span class="p">>,<</span><span class="n">element</span><span class="p">>,...)</span>
<span class="nv">$var</span><span class="p">[</span><span class="n">0</span><span class="p">]</span>
<span class="nv">$var</span><span class="p">[</span><span class="n">100</span><span class="p">]=</span><span class="n">2333</span>
</pre></div>
<h3>Hash Table</h3>
<div class="highlight"><pre><span></span><span class="nv">$var</span><span class="p">=@{<</span><span class="n">key</span><span class="p">>=<</span><span class="n">value</span><span class="p">>,...}</span>
<span class="nv">$var</span><span class="p">[<</span><span class="n">key</span><span class="p">>]</span>
<span class="nv">$var</span><span class="p">.</span><span class="n">key</span>
</pre></div>
<h2>Process Control</h2>
<h3>Branch</h3>
<div class="highlight"><pre><span></span><span class="k">if</span><span class="p">()</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">elseif</span><span class="p">()</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">else</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
</pre></div>
<div class="highlight"><pre><span></span><span class="k">switch</span><span class="p">(</span><span class="nv">$x</span><span class="p">)</span>
<span class="p">{</span>
<span class="n">condition</span> <span class="p">{...;</span><span class="k">break</span><span class="p">}</span>
<span class="k">default</span> <span class="p">{...}</span>
<span class="p">}</span>
</pre></div>
<div class="highlight"><pre><span></span><span class="o">-</span><span class="n">gt</span> <span class="n">greater</span> <span class="k">than</span>
<span class="o">-</span><span class="n">lt</span> <span class="k">less</span> <span class="k">than</span>
<span class="o">-</span><span class="n">eq</span> <span class="n">equal</span>
</pre></div>
<h3>Circulation</h3>
<div class="highlight"><pre><span></span><span class="k">for</span><span class="p">(;;)</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
</pre></div>
<div class="highlight"><pre><span></span><span class="k">foreach</span><span class="p">(</span><span class="nv">$var</span> <span class="k">in</span> <span class="nv">$set</span><span class="p">)</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
</pre></div>
<div class="highlight"><pre><span></span><span class="k">while</span><span class="p">()</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">do</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="k">while</span><span class="p">/</span><span class="k">until</span><span class="p">()</span>
</pre></div>
<h1>.NET & Class</h1>
<h2>Class</h2>
<div class="highlight"><pre><span></span><span class="c">#show all members of a object</span>
<span class="nv">$var</span> <span class="p">|</span> <span class="nb">gm</span>
<span class="c">#call member function</span>
<span class="nv">$var</span><span class="p">.</span><span class="n">fun</span><span class="p">()</span>
<span class="c">#visit member variable</span>
<span class="nv">$var</span><span class="p">.</span><span class="n">var</span>
</pre></div>
<h2>.NET</h2>
<p>some methods to creat a new object</p>
<div class="highlight"><pre><span></span><span class="nv">$obj</span> <span class="p">=</span> <span class="nb">New-Object</span> <span class="n">System</span><span class="p">.</span><span class="n">Version</span>
<span class="nv">$obj</span>
<span class="nv">$obj</span> <span class="p">=</span> <span class="nb">New-Object</span> <span class="n">System</span><span class="p">.</span><span class="n">Version</span> <span class="n">3</span> <span class="n">6</span>
<span class="nv">$obj</span>
<span class="nv">$obj</span> <span class="p">=</span> <span class="no">[System.Version]</span><span class="p">::</span><span class="n">New</span><span class="p">()</span>
<span class="nv">$obj</span>
<span class="nv">$obj</span> <span class="p">=</span> <span class="no">[System.Version]</span><span class="p">::</span><span class="n">New</span><span class="p">(</span><span class="n">3</span><span class="p">,</span><span class="n">6</span><span class="p">)</span>
<span class="nv">$obj</span>
</pre></div>
<p>type conversion</p>
<div class="highlight"><pre><span></span><span class="nv">$obj</span><span class="p">.</span><span class="n">ToString</span><span class="p">()</span>
<span class="no">[int]</span><span class="n">1</span><span class="p">.</span><span class="n">7</span>
<span class="no">[System.Version]</span><span class="s1">'3.6.0.0'</span>
</pre></div>
<h2>Create a Class</h2>
<div class="highlight"><pre><span></span><span class="n">class</span> <span class="n">MyClass</span>
<span class="p">{</span>
<span class="p"><</span><span class="n">hidden</span><span class="p">|</span><span class="n">static</span><span class="p">></span>
<span class="no">[typename]</span><span class="p">$<</span><span class="n">member</span><span class="p">></span>
<span class="n">MyClass</span><span class="p">()</span><span class="c">#Constructor</span>
<span class="p">{</span>
<span class="p">...</span>
<span class="p">}</span>
<span class="p">}</span>
</pre></div>boost learning note (2) Boost.Core2018-11-20T00:00:00+08:002018-11-20T00:00:00+08:00fx-moontag:www.git.moe,2018-11-20:/boost-learning-note-2-boostcore.html<h1>Introduction</h1>
<p>The Boost.Core library is a collection of core utilities.
The criteria for inclusion is that the utility component be:</p>
<ul>
<li>simple</li>
<li>used by other Boost librarys, and</li>
<li>not dependent on any other Boost modules except Core itself, Config, Assert, Static Assert, or Predef.</li>
</ul>
<h1>addressof</h1>
<h2>Overview</h2>
<p>The header <code><boost/core …</code></p><h1>Introduction</h1>
<p>The Boost.Core library is a collection of core utilities.
The criteria for inclusion is that the utility component be:</p>
<ul>
<li>simple</li>
<li>used by other Boost librarys, and</li>
<li>not dependent on any other Boost modules except Core itself, Config, Assert, Static Assert, or Predef.</li>
</ul>
<h1>addressof</h1>
<h2>Overview</h2>
<p>The header <code><boost/core/addressof.hpp></code> defines the function template <code>boost::addressof.boost::addressof(x)</code> returns the address of x.
Ordinarily, this address can be obtained by <code>&x</code>, but the unary <code>&</code> operator can be overloaded.
boost::addressof avoids calling used-defined <code>operator&()</code>.</p>
<h2>Synopsis</h2>
<div class="highlight"><pre><span></span><span class="k">namespace</span> <span class="n">boost</span>
<span class="p">{</span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="n">T</span><span class="o">*</span> <span class="n">addressof</span><span class="p">(</span><span class="n">T</span><span class="o">&</span> <span class="n">x</span><span class="p">);</span>
<span class="p">}</span>
</pre></div>
<h2>Example</h2>
<div class="highlight"><pre><span></span><span class="cp">#include</span><span class="cpf"><boost/core/addressof.hpp></span><span class="cp"></span>
<span class="k">struct</span> <span class="n">useless_type</span> <span class="p">{</span> <span class="p">};</span>
<span class="k">class</span> <span class="nc">nonaddressable</span>
<span class="p">{</span>
<span class="n">useless_type</span> <span class="k">operator</span><span class="o">&</span> <span class="k">const</span><span class="p">;</span>
<span class="p">};</span>
<span class="kt">void</span> <span class="nf">f</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">nonaddressable</span> <span class="n">x</span><span class="p">;</span>
<span class="n">nonaddressable</span><span class="o">*</span> <span class="n">xp</span> <span class="o">=</span> <span class="n">boost</span><span class="o">::</span><span class="n">addressof</span><span class="p">(</span><span class="n">x</span><span class="p">);</span>
<span class="c1">// nonaddressable* xpe = &x; /*error*/</span>
<span class="p">}</span>
</pre></div>
<h2>Notes</h2>
<blockquote>
<p>In C++11 and above. boost::address is conditionally constexpr when possible. This is indicated by BOOST_CORE_NO_CONSTEXPR_ADDRESSOF not being defined.</p>
<p>With supported compilers, boost::addressof is always constexpr by leveraging compiler intrinsics. This is indicated by BOOST_CORE_HAS_BUILTIN_ADDRESSOF being defined.</p>
</blockquote>
<h1>checked_delete</h1>
<h2>Overview</h2>
<p>The header <code><boost/checked_delete.hpp></code> defines two function templates, <code>checked_delete</code> and <code>checked_array_delete</code>, and two class templates, <code>checked_deleter</code> and <code>checked_array_deleter</code>.</p>
<p>The C++ Standard allows, in 5.3.5/5, pointers to incomplete class types to be deleted with a delete-expression. When the class has a non-trivial destructor, or a class-specific operator delete, the behavior is undefined. Some compilers issue a warning when an incomplete type is deleted, but unfortunately, not all do, and programmers sometimes ignore or disable warnings.</p>
<p>A particularly troublesome case is when a smart pointer's destructor, such as <code>boost::scoped_ptr<T>::~scoped_ptr</code>, is instantiated with an incomplete type. This can often lead to silent, hard to track failures.</p>
<p>The supplied function and class templates can be used to prevent these problems, as they require a complete type, and cause a compilation error otherwise.</p>
<h2>Synopsis</h2>
<div class="highlight"><pre><span></span><span class="k">namespace</span> <span class="n">boost</span>
<span class="p">{</span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="kt">void</span> <span class="n">checked_delete</span><span class="p">(</span><span class="n">T</span><span class="o">*</span> <span class="n">p</span><span class="p">);</span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="kt">void</span> <span class="n">checked_array_delete</span><span class="p">(</span><span class="n">T</span><span class="o">*</span> <span class="n">p</span><span class="p">);</span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">checked_deleter</span><span class="p">;</span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">checked_array_deleter</span><span class="p">;</span>
<span class="p">}</span>
</pre></div>
<h2>checked_delete</h2>
<div class="highlight"><pre><span></span><span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span><span class="kt">void</span> <span class="n">checked_delete</span><span class="p">(</span><span class="n">T</span><span class="o">*</span> <span class="n">p</span><span class="p">);</span>
</pre></div>
<ul>
<li>Requires: T must be a complete type. The expression <code>delete p</code> must be well-formed.</li>
<li>Effects: <code>delete p;</code></li>
</ul>
<h2>checked_array_delete</h2>
<div class="highlight"><pre><span></span><span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="kt">void</span> <span class="n">checked_array_delete</span><span class="p">(</span><span class="n">T</span> <span class="o">*</span> <span class="n">p</span><span class="p">);</span>
</pre></div>
<ul>
<li>Requires: T must be a complete type. The expression <code>delete [] p</code> must be well formed.</li>
<li>Effects: <code>delete [] p;</code></li>
</ul>
<h1>demangle</h1>
<h2>Overview</h2>
<p>The header <code><boost/core/demangle.hpp></code> defines several tools for undecorating symbol names.</p>
<h2>Synopsis</h2>
<div class="highlight"><pre><span></span><span class="k">namespace</span> <span class="n">boost</span>
<span class="p">{</span>
<span class="k">namespace</span> <span class="n">core</span>
<span class="p">{</span>
<span class="n">std</span><span class="o">::</span><span class="n">string</span> <span class="n">demangle</span><span class="p">(</span> <span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">name</span> <span class="p">);</span>
<span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="nf">demangle_alloc</span><span class="p">(</span> <span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">name</span> <span class="p">)</span> <span class="k">noexcept</span><span class="p">;</span>
<span class="kt">void</span> <span class="nf">demangle_free</span><span class="p">(</span> <span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">demangled_name</span> <span class="p">)</span> <span class="k">noexcept</span><span class="p">;</span>
<span class="k">class</span> <span class="nc">scoped_demangled_name</span>
<span class="p">{</span>
<span class="k">public</span><span class="o">:</span>
<span class="k">explicit</span> <span class="n">scoped_demangled_name</span><span class="p">(</span> <span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">name</span> <span class="p">)</span> <span class="k">noexcept</span><span class="p">;</span>
<span class="o">~</span><span class="n">scoped_demangled_name</span><span class="p">()</span> <span class="k">noexcept</span><span class="p">;</span>
<span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="nf">get</span><span class="p">()</span> <span class="k">const</span> <span class="k">noexcept</span><span class="p">;</span>
<span class="n">scoped_demangled_name</span><span class="p">(</span> <span class="n">scoped_demangled_name</span> <span class="k">const</span><span class="o">&</span> <span class="p">)</span> <span class="o">=</span> <span class="k">delete</span><span class="p">;</span>
<span class="n">scoped_demangled_name</span><span class="o">&</span> <span class="k">operator</span><span class="o">=</span> <span class="p">(</span> <span class="n">scoped_demangled_name</span> <span class="k">const</span><span class="o">&</span> <span class="p">)</span> <span class="o">=</span> <span class="k">delete</span><span class="p">;</span>
<span class="p">};</span>
<span class="p">}</span>
<span class="p">}</span>
</pre></div>
<h2>Conventional interface</h2>
<p>The function <code>boost::core::demangle</code> is the conventional way to obtain demangled symbol name. It takes a mangled string such as those returned by <code>typeid(T).name()</code> on certain implementations such as <code>g++</code>, and returns its demangled, human-readable, form. In case if demangling fails (e.g. if name cannot be interpreted as a mangled name) the function returns name.</p>
<h3>Example</h3>
<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><boost/core/demangle.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><typeinfo></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">X</span>
<span class="p">{</span>
<span class="p">};</span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">name</span> <span class="o">=</span> <span class="k">typeid</span><span class="p">(</span> <span class="n">X</span><span class="o"><</span><span class="kt">int</span><span class="o">></span> <span class="p">).</span><span class="n">name</span><span class="p">();</span>
<span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="n">name</span> <span class="o"><<</span> <span class="n">std</span><span class="o">::</span><span class="n">endl</span><span class="p">;</span> <span class="c1">// prints 1XIiE</span>
<span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="n">boost</span><span class="o">::</span><span class="n">core</span><span class="o">::</span><span class="n">demangle</span><span class="p">(</span> <span class="n">name</span> <span class="p">)</span> <span class="o"><<</span> <span class="n">std</span><span class="o">::</span><span class="n">endl</span><span class="p">;</span> <span class="c1">// prints X<int></span>
<span class="p">}</span>
</pre></div>
<h2>Low level interface</h2>
<p>In some cases more low level interface may be desirable. For example:</p>
<ul>
<li>Assuming that symbol demangling may fail, the user wants to be able to handle such errors.</li>
<li>The user needs to post-process the demangled name (e.g. remove common namespaces), and allocating a temporary string with the complete demangled name is significant overhead.</li>
</ul>
<p>The function <code>boost::core::demangle_alloc</code> performs name demangling and returns a pointer to a string with the demangled name, if succeeded, or nullptr otherwise. The returned pointer must be passed to <code>boost::core::demangle_free</code> to reclaim resources. Note that on some platforms the pointer returned by <code>boost::core::demangle_alloc</code> may refer to the string denoted by name, so this string must be kept immutable for the whole life time of the returned pointer.</p>
<p>The <code>boost::core::scoped_demangled_name</code> class is a scope guard that automates the calls to <code>boost::core::demangle_alloc</code> (on its construction) and <code>boost::core::demangle_free</code> (on destruction). The string with the demangled name can be obtained with its get method. Note that this method may return <code>nullptr</code> if demangling failed.</p>
<h3>Example</h3>
<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><boost/core/demangle.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><typeinfo></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="k">template</span><span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">X</span>
<span class="p">{</span>
<span class="p">};</span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="kt">char</span> <span class="k">const</span> <span class="o">*</span> <span class="n">name</span> <span class="o">=</span> <span class="k">typeid</span><span class="p">(</span> <span class="n">X</span><span class="o"><</span><span class="kt">int</span><span class="o">></span> <span class="p">).</span><span class="n">name</span><span class="p">();</span>
<span class="n">boost</span><span class="o">::</span><span class="n">core</span><span class="o">::</span><span class="n">scoped_demangled_name</span> <span class="n">demangled</span><span class="p">(</span> <span class="n">name</span> <span class="p">);</span>
<span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="n">name</span> <span class="o"><<</span> <span class="n">std</span><span class="o">::</span><span class="n">endl</span><span class="p">;</span> <span class="c1">// prints 1XIiE</span>
<span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="p">(</span><span class="n">demangled</span><span class="p">.</span><span class="n">get</span><span class="p">()</span> <span class="o">?</span> <span class="n">demangled</span><span class="p">.</span><span class="n">get</span><span class="p">()</span> <span class="o">:</span> <span class="s">"[unknown]"</span><span class="p">)</span> <span class="o"><<</span> <span class="n">std</span><span class="o">::</span><span class="n">endl</span><span class="p">;</span> <span class="c1">// prints X<int></span>
<span class="p">}</span>
</pre></div>
<h1>enable_if</h1>
<h2>Overview</h2>
<p>The <code>enable_if</code> family of templates is a set of tools to allow a function template or a class template specialization to include or exclude itself from a set of matching functions or specializations based on properties of its template arguments. For example, one can define function templates that are only enabled for, and thus only match, an arbitrary set of types defined by a traits class. The enable_if templates can also be applied to enable class template specializations. Applications of enable_if are discussed in length in [1] and [2].</p>
<h2>Synopsis</h2>
<div class="highlight"><pre><span></span><span class="k">namespace</span> <span class="n">boost</span> <span class="p">{</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">Cond</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span> <span class="k">struct</span> <span class="n">enable_if</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">Cond</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span> <span class="k">struct</span> <span class="n">disable_if</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">Cond</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">lazy_enable_if</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">Cond</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">lazy_disable_if</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="kt">bool</span> <span class="n">B</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span> <span class="k">struct</span> <span class="n">enable_if_c</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="kt">bool</span> <span class="n">B</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span> <span class="k">struct</span> <span class="n">disable_if_c</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="kt">bool</span> <span class="n">B</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">lazy_enable_if_c</span><span class="p">;</span>
<span class="k">template</span> <span class="o"><</span><span class="kt">bool</span> <span class="n">B</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span><span class="o">></span> <span class="k">struct</span> <span class="n">lazy_disable_if_c</span><span class="p">;</span>
<span class="p">}</span>
</pre></div>
<h2>Background</h2>
<p>Sensible operation of template function overloading in C++ relies on the <strong>SFINAE</strong> (substitution-failure-is-not-an-error) principle [3]: if an invalid argument or return type is formed during the instantiation of a function template, the instantiation is removed from the overload resolution set instead of causing a compilation error. The following example, taken from [1], demonstrates why this is important:</p>
<div class="highlight"><pre><span></span><span class="kt">int</span> <span class="nf">negate</span><span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="o">-</span><span class="n">i</span><span class="p">;</span> <span class="p">}</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">F</span><span class="o">></span>
<span class="k">typename</span> <span class="n">F</span><span class="o">::</span><span class="n">result_type</span> <span class="n">negate</span><span class="p">(</span><span class="k">const</span> <span class="n">F</span><span class="o">&</span> <span class="n">f</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="o">-</span><span class="n">f</span><span class="p">();</span> <span class="p">}</span>
</pre></div>
<p>Suppose the compiler encounters the call <code>negate(1)</code>. The first definition is obviously a better match, but the compiler must nevertheless consider (and instantiate the prototypes) of both definitions to find this out. Instantiating the latter definition with <code>F</code> as <code>int</code> would result in:</p>
<div class="highlight"><pre><span></span><span class="kt">int</span><span class="o">::</span><span class="n">result_type</span> <span class="n">negate</span><span class="p">(</span><span class="k">const</span> <span class="kt">int</span><span class="o">&</span><span class="p">);</span>
</pre></div>
<p>where the return type is invalid. If this were an error, adding an unrelated function template (that was never called) could break otherwise valid code. Due to the SFINAE principle the above example is not, however, erroneous. The latter definition of <code>negate</code> is simply removed from the overload resolution set.</p>
<p>The <code>enable_if</code> templates are tools for controlled creation of the <strong>SFINAE</strong> conditions.</p>
<h2>The enable_if templates</h2>
<p>The names of the <code>enable_if</code> templates have three parts: an optional <code>lazy_</code> tag, either <code>enable_if</code> or <code>disable_if</code>, and an optional <code>_c</code> tag. All eight combinations of these parts are supported. The meaning of the <code>lazy_</code> tag is described in the section below. The second part of the name indicates whether a true condition argument should enable or disable the current overload. The third part of the name indicates whether the condition argument is a <code>bool</code> value (<code>_c</code> suffix), or a type containing a <code>static bool</code> constant named <code>value</code> (no suffix). The latter version interoperates with Boost.MPL.</p>
<p>The definitions of <code>enable_if_c</code> and <code>enable_if</code> are as follows (we use <code>enable_if</code> templates unqualified but they are in the <code>boost</code> namespace).</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="kt">bool</span> <span class="n">B</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span>
<span class="k">struct</span> <span class="n">enable_if_c</span> <span class="p">{</span>
<span class="k">typedef</span> <span class="n">T</span> <span class="n">type</span><span class="p">;</span>
<span class="p">};</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="k">struct</span> <span class="n">enable_if_c</span><span class="o"><</span><span class="nb">false</span><span class="p">,</span> <span class="n">T</span><span class="o">></span> <span class="p">{};</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">Cond</span><span class="p">,</span> <span class="k">class</span> <span class="nc">T</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span>
<span class="k">struct</span> <span class="nl">enable_if</span> <span class="p">:</span> <span class="k">public</span> <span class="n">enable_if_c</span><span class="o"><</span><span class="n">Cond</span><span class="o">::</span><span class="n">value</span><span class="p">,</span> <span class="n">T</span><span class="o">></span> <span class="p">{};</span>
</pre></div>
<p>An instantiation of the <code>enable_if_c</code> template with the parameter <code>B</code> as <code>true</code> contains a member type <code>type</code>, defined to be <code>T</code>. If <code>B</code> is false, no such member is defined. Thus <code>enable_if_c<B, T>::type</code> is either a valid or an invalid type expression, depending on the value of <code>B</code>. When valid, <code>enable_if_c<B, T>::type</code> equals <code>T</code>. The <code>enable_if_c</code> template can thus be used for controlling when functions are considered for overload resolution and when they are not. For example, the following function is defined for all arithmetic types (according to the classification of the Boost <strong>type_traits</strong> library):</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="k">typename</span> <span class="n">enable_if_c</span><span class="o"><</span><span class="n">boost</span><span class="o">::</span><span class="n">is_arithmetic</span><span class="o"><</span><span class="n">T</span><span class="o">>::</span><span class="n">value</span><span class="p">,</span> <span class="n">T</span><span class="o">>::</span><span class="n">type</span>
<span class="n">foo</span><span class="p">(</span><span class="n">T</span> <span class="n">t</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">t</span><span class="p">;</span> <span class="p">}</span>
</pre></div>
<p>The <code>disable_if_c</code> template is provided as well, and has the same functionality as <code>enable_if_c</code> except for the negated condition. The following function is enabled for all non-arithmetic types.</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="k">typename</span> <span class="n">disable_if_c</span><span class="o"><</span><span class="n">boost</span><span class="o">::</span><span class="n">is_arithmetic</span><span class="o"><</span><span class="n">T</span><span class="o">>::</span><span class="n">value</span><span class="p">,</span> <span class="n">T</span><span class="o">>::</span><span class="n">type</span>
<span class="n">bar</span><span class="p">(</span><span class="n">T</span> <span class="n">t</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">t</span><span class="p">;</span> <span class="p">}</span>
</pre></div>
<p>For easier syntax in some cases and interoperation with Boost.MPL we provide versions of the <code>enable_if</code> templates taking any type with a <code>bool</code> member constant named <code>value</code> as the condition argument. The MPL <code>bool_</code>, <code>and_</code>, <code>or_</code>, and <code>not_</code> templates are likely to be useful for creating such types. Also, the traits classes in the <code>Boost.Type_traits</code> library follow this convention. For example, the above example function <code>foo</code> can be alternatively written as:</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="k">typename</span> <span class="n">enable_if</span><span class="o"><</span><span class="n">boost</span><span class="o">::</span><span class="n">is_arithmetic</span><span class="o"><</span><span class="n">T</span><span class="o">></span><span class="p">,</span> <span class="n">T</span><span class="o">>::</span><span class="n">type</span>
<span class="n">foo</span><span class="p">(</span><span class="n">T</span> <span class="n">t</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">t</span><span class="p">;</span> <span class="p">}</span>
</pre></div>
<h2>Using enable_if</h2>
<p>The <code>enable_if</code> templates are defined in <code>boost/utility/enable_if.hpp</code>, which is included by <code>boost/utility.hpp</code>.</p>
<p>With respect to function templates, <code>enable_if</code> can be used in multiple different ways:</p>
<ul>
<li>As the return type of an instantiatied function</li>
<li>As an extra parameter of an instantiated function</li>
<li>As an extra template parameter (useful only in a compiler that supports <code>C++0x</code> default arguments for function template parameters, see <a href="https://www.boost.org/doc/libs/1_68_0/libs/core/doc/html/core/enable_if.html#core.enable_if.using_enable_if.enable_if_0x"><em>Enabling function templates</em> in <code>C++0x</code></a> for details.</li>
</ul>
<p>In the previous section, the return type form of enable_if was shown. As an example of using the form of enable_if that works via an extra function parameter, the foo function in the previous section could also be written as:</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="n">T</span> <span class="n">foo</span><span class="p">(</span><span class="n">T</span> <span class="n">t</span><span class="p">,</span> <span class="k">typename</span> <span class="n">enable_if</span><span class="o"><</span><span class="n">boost</span><span class="o">::</span><span class="n">is_arithmetic</span><span class="o"><</span><span class="n">T</span><span class="o">></span> <span class="o">>::</span><span class="n">type</span><span class="o">*</span> <span class="n">dummy</span> <span class="o">=</span> <span class="mi">0</span><span class="p">);</span>
</pre></div>
<p>Hence, an extra parameter of type <code>void*</code> is added, but it is given a default value to keep the parameter hidden from client code. Note that the second template argument was not given to <code>enable_if</code>, as the default <code>void</code> gives the desired behavior.</p>
<p>Which way to write the enabler is largely a matter of taste, but for certain functions, only a subset of the options is possible:</p>
<ul>
<li>Many operators have a fixed number of arguments, thus enable_if must be used either in the return type or in an extra template parameter.</li>
<li>Functions that have a variadic parameter list must use either the return type form or an extra template parameter.</li>
<li>Constructors do not have a return type so you must use either an extra function parameter or an extra template parameter.</li>
<li>Constructors that have a variadic parameter list must an extra template parameter.</li>
<li>Conversion operators can only be written with an extra template parameter.</li>
</ul>
<h2>Enabling function templates in C++0x</h2>
<p>In a compiler which supports C++0x default arguments for function template parameters, you can enable and disable function templates by adding an additional template parameter. This approach works in all situations where you would use either the return type form of enable_if or the function parameter form, including operators, constructors, variadic function templates, and even overloaded conversion operations.</p>
<p>As an example:</p>
<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><boost/type_traits/is_arithmetic.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><boost/type_traits/is_pointer.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><boost/utility/enable_if.hpp></span><span class="cp"></span>
<span class="k">class</span> <span class="nc">test</span>
<span class="p">{</span>
<span class="k">public</span><span class="o">:</span>
<span class="c1">// A constructor that works for any argument list of size 10</span>
<span class="k">template</span><span class="o"><</span> <span class="n">class</span><span class="p">...</span> <span class="n">T</span><span class="p">,</span>
<span class="k">typename</span> <span class="n">boost</span><span class="o">::</span><span class="n">enable_if_c</span><span class="o"><</span> <span class="k">sizeof</span><span class="p">...(</span> <span class="n">T</span> <span class="p">)</span> <span class="o">==</span> <span class="mi">10</span><span class="p">,</span>
<span class="kt">int</span> <span class="o">>::</span><span class="n">type</span> <span class="o">=</span> <span class="mi">0</span><span class="o">></span>
<span class="n">test</span><span class="p">(</span> <span class="n">T</span><span class="o">&&</span><span class="p">...</span> <span class="p">);</span>
<span class="c1">// A conversion operation that can convert to any arithmetic type</span>
<span class="k">template</span><span class="o"><</span> <span class="k">class</span> <span class="nc">T</span><span class="p">,</span>
<span class="k">typename</span> <span class="n">boost</span><span class="o">::</span><span class="n">enable_if</span><span class="o"><</span> <span class="n">boost</span><span class="o">::</span><span class="n">is_arithmetic</span><span class="o"><</span> <span class="n">T</span> <span class="o">></span><span class="p">,</span>
<span class="kt">int</span> <span class="o">>::</span><span class="n">type</span> <span class="o">=</span> <span class="mi">0</span><span class="o">></span>
<span class="k">operator</span> <span class="n">T</span><span class="p">()</span> <span class="k">const</span><span class="p">;</span>
<span class="c1">// A conversion operation that can convert to any pointer type</span>
<span class="k">template</span><span class="o"><</span> <span class="k">class</span> <span class="nc">T</span><span class="p">,</span>
<span class="k">typename</span> <span class="n">boost</span><span class="o">::</span><span class="n">enable_if</span><span class="o"><</span> <span class="n">boost</span><span class="o">::</span><span class="n">is_pointer</span><span class="o"><</span> <span class="n">T</span> <span class="o">></span><span class="p">,</span>
<span class="kt">int</span> <span class="o">>::</span><span class="n">type</span> <span class="o">=</span> <span class="mi">0</span><span class="o">></span>
<span class="k">operator</span> <span class="n">T</span><span class="p">()</span> <span class="k">const</span><span class="p">;</span>
<span class="p">};</span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="c1">// Works</span>
<span class="n">test</span> <span class="n">test_</span><span class="p">(</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">,</span> <span class="mi">7</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">10</span> <span class="p">);</span>
<span class="c1">// Fails as expected</span>
<span class="n">test</span> <span class="n">fail_construction</span><span class="p">(</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">5</span> <span class="p">);</span>
<span class="c1">// Works by calling the conversion operator enabled for arithmetic types</span>
<span class="kt">int</span> <span class="n">arithmetic_object</span> <span class="o">=</span> <span class="n">test_</span><span class="p">;</span>
<span class="c1">// Works by calling the conversion operator enabled for pointer types</span>
<span class="kt">int</span><span class="o">*</span> <span class="n">pointer_object</span> <span class="o">=</span> <span class="n">test_</span><span class="p">;</span>
<span class="c1">// Fails as expected</span>
<span class="k">struct</span> <span class="p">{}</span> <span class="n">fail_conversion</span> <span class="o">=</span> <span class="n">test_</span><span class="p">;</span>
<span class="p">}</span>
</pre></div>
<h2>Enabling template class specializations</h2>
<p>Class template specializations can be enabled or disabled with <code>enable_if</code>. One extra template parameter needs to be added for the enabler expressions. This parameter has the default value <code>void</code>. For example:</p>
<div class="highlight"><pre><span></span><span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="p">,</span> <span class="k">class</span> <span class="nc">Enable</span> <span class="o">=</span> <span class="kt">void</span><span class="o">></span>
<span class="k">class</span> <span class="nc">A</span> <span class="p">{...};</span>
<span class="k">template</span> <span class="o"><</span><span class="k">class</span> <span class="nc">T</span><span class="o">></span>
<span class="k">class</span> <span class="nc">A</span><span class="o"><</span><span class="n">T</span><span class="p">,</span> <span class="k">typename</span> <span class="n">enable_if</span><span class="o"><</span><span class="n">is_integral</span><span class="o"><</span><span class="n">T</span><span class="o">></span> <span class="o">>::</span><span class="n">type</span><span class="o">></span> <span class="p">{...};</span>
<span class="k">template</span> <span class="o"><</span><span class="n">claas</span> <span class="n">T</span><span class="o">></span>
<span class="k">class</span> <span class="nc">A</span><span class="o"><</span><span class="n">T</span><span class="p">,</span> <span class="k">typename</span> <span class="n">enable_if</span><span class="o"><</span><span class="n">is_float</span><span class="o"><</span><span class="n">T</span><span class="o">></span> <span class="o">>::</span><span class="n">type</span><span class="o">></span> <span class="p">{...};</span>
</pre></div>
<p>Instantiating <code>A</code> with any integral type matches the first specialization, whereas any floating point type matches the second one. All other tklypes match the primary template. The condition can be an;y compile-time boolean expression that depends on the template arguments of the dependent <code>value_type</code> from <code>T</code>if and only if <code>T::value_type</code> exists.</p>boost learning note (1) getting started on Windows2018-11-12T00:00:00+08:002018-11-12T00:00:00+08:00fx-moontag:www.git.moe,2018-11-12:/boost-learning-note-1-getting-started-on-windows.html<h1>1 Get boost</h1>
<p>just find a copy on <a href="https://www.boost.org">https://www.boost.org</a></p>
<h1>2 The boost distribution</h1>
<div class="highlight"><pre><span></span>boost_1_67_0<span class="se">\ </span>.................The “boost root directory”
index.htm .........A copy of www.boost.org starts here
boost<span class="se">\ </span>.........................All Boost Header files
lib<span class="se">\ </span>.....................precompiled library binaries
libs<span class="se">\ </span>............Tests, .cpps, docs, etc., by library
index.html ........Library …</pre></div><h1>1 Get boost</h1>
<p>just find a copy on <a href="https://www.boost.org">https://www.boost.org</a></p>
<h1>2 The boost distribution</h1>
<div class="highlight"><pre><span></span>boost_1_67_0<span class="se">\ </span>.................The “boost root directory”
index.htm .........A copy of www.boost.org starts here
boost<span class="se">\ </span>.........................All Boost Header files
lib<span class="se">\ </span>.....................precompiled library binaries
libs<span class="se">\ </span>............Tests, .cpps, docs, etc., by library
index.html ........Library documentation starts here
algorithm<span class="se">\</span>
any<span class="se">\</span>
array<span class="se">\</span>
…more libraries…
status<span class="se">\ </span>.........................Boost-wide <span class="nb">test</span> suite
tools<span class="se">\ </span>...........Utilities, e.g. Boost.Build, quickbook, bcp
more<span class="se">\ </span>..........................Policy documents, etc.
doc<span class="se">\ </span>...............A subset of all Boost library docs
</pre></div>
<ol>
<li>The path to the <strong>boost root directory</strong> (often C:\Program Files\boost\boost_1_67_0) is sometimes referred to as <em>$BOOST_ROOT</em> in documentation and mailing lists .</li>
<li>To compile anything in Boost, you need a directory containing the <code>boost\</code> subdirectory in your <code>#include</code> path. Specific steps for setting up <code>#include</code> paths in Microsoft Visual Studio follow later in this document; if you use another IDE, please consult your product's documentation for instructions.</li>
<li>Since all of Boost's header files have the <code>.hpp</code> extension, and live in the <code>boost\</code> subdirectory of the boost root, your Boost <code>#include</code> directives will look like:
<code>c
#include <boost/whatever.hpp></code>
or
<code>c
#include "boost/whatever.hpp"</code>
depending on your preference regarding the use of angle bracket includes. Even Windows users can (and, for portability reasons, probably should) use forward slashes in #include directives; your compiler doesn't care.</li>
<li>Don't be distracted by the <code>doc\</code> subdirectory; it only contains a subset of the Boost documentation. Start with <code>libs\index.html</code> if you're looking for the whole enchilada.<blockquote>
<h2>Header Organization</h2>
<p>The organization of Boost library headers isn't entirely uniform, but most libraries follow a few patterns:
* Some older libraries and most very small libraries place all public headers directly into <code>boost\</code>.
* Most libraries' public headers live in a subdirectory of boost\, named after the library. For example, you'll find the Python library's def.hpp header in
<code>bash
boost\python\def.hpp.</code>
* Some libraries have an “aggregate header” in boost\ that #includes all of the library's other headers. For example, Boost.Python's aggregate header is
<code>bash
boost\python.hpp.</code>
* Most libraries place private headers in a subdirectory called <code>detail\</code>, or <code>aux_\</code>. Don't expect to find anything you can use in these directories.</p>
</blockquote>
</li>
</ol>
<h1>3 Header-Only Libraries</h1>
<p>The first thing many people want to know is, “how do I build Boost?” The good news is that often, there's nothing to build.</p>
<blockquote>
<h2>Nothing to Build?</h2>
<p>Most Boost libraries are header-only: they consist entirely of header files containing templates and inline functions, and require no separately-compiled library binaries or special treatment when linking.</p>
</blockquote>
<p>The only Boost libraries that must be built separately are:</p>
<ul>
<li>Boost.Chrono</li>
<li>Boost.Context</li>
<li>Boost.Filesystem</li>
<li>Boost.GraphParallel</li>
<li>Boost.IOStreams</li>
<li>Boost.Locale</li>
<li>Boost.Log <code>(see build documentation)</code></li>
<li>Boost.MPI</li>
<li>Boost.ProgramOptions</li>
<li>Boost.Python <code>(see the Boost.Python build documentation before building and installing it)</code></li>
<li>Boost.Regex</li>
<li>Boost.Serialization</li>
<li>Boost.Signals</li>
<li>Boost.System</li>
<li>Boost.Thread</li>
<li>Boost.Timer</li>
<li>Boost.Wave</li>
</ul>
<p>A few libraries have optional separately-compiled binaries:</p>
<ul>
<li><strong>Boost.DateTime</strong> has a binary component that is only needed if you're using its to_string/from_string or serialization features, or if you're targeting Visual C++ 6.x or Borland.</li>
<li><strong>Boost.Graph</strong> also has a binary component that is only needed if you intend to parse GraphViz files.</li>
<li><strong>Boost.Math</strong> has binary components for the TR1 and C99 cmath functions.</li>
<li><strong>Boost.Random</strong> has a binary component which is only needed if you're using random_device.</li>
<li><strong>Boost.Test</strong> can be used in “header-only” or “separately compiled” mode, although <em>separate compilation is recommended for serious use</em>.</li>
<li><strong>Boost.Exception</strong> provides non-intrusive implementation of <code>exception_ptr</code> for 32-bit <code>_MSC_VER==1310</code> and <code>_MSC_VER==1400</code> which requires a separately-compiled binary. This is enabled by <code>#define BOOST_ENABLE_NON_INTRUSIVE_EXCEPTION_PTR</code>.</li>
</ul>
<h1>4 Build a Simple Program Using Boost</h1>
<p>To keep things simple, let's start by using a header-only library. The following program reads a sequence of integers from standard input, uses Boost.Lambda to multiply each number by three, and writes them to standard output:</p>
<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><boost/lambda/lambda.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><iterator></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><algorithm></span><span class="cp"></span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="k">using</span> <span class="k">namespace</span> <span class="n">boost</span><span class="o">::</span><span class="n">lambda</span><span class="p">;</span>
<span class="k">typedef</span> <span class="n">std</span><span class="o">::</span><span class="n">istream_iterator</span><span class="o"><</span><span class="kt">int</span><span class="o">></span> <span class="n">in</span><span class="p">;</span>
<span class="n">std</span><span class="o">::</span><span class="n">for_each</span><span class="p">(</span>
<span class="n">in</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">cin</span><span class="p">),</span> <span class="n">in</span><span class="p">(),</span> <span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="p">(</span><span class="n">_1</span> <span class="o">*</span> <span class="mi">3</span><span class="p">)</span> <span class="o"><<</span> <span class="s">" "</span> <span class="p">);</span>
<span class="p">}</span>
</pre></div>
<p>Copy the text of this program into a file called example.cpp.</p>
<blockquote>
<p><strong>Note</strong></p>
<p>To build the examples in this guide, you can use an Integrated Development Environment (IDE) like Visual Studio, or you can issue commands from the <a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#command-prompt">command prompt</a>. Since every IDE and compiler has different options and Microsoft's are by far the dominant compilers on Windows, we only give specific directions here for Visual Studio 2005 and .NET 2003 IDEs and their respective command prompt compilers (using the command prompt is a bit simpler). If you are using another compiler or IDE, it should be relatively easy to adapt these instructions to your environment.</p>
</blockquote>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#build-from-the-visual-studio-ide">4.1 Build From the Visual Studio IDE</a></h2>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#or-build-from-the-command-prompt">4.2 Or, Build From the Command Prompt</a></h2>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#errors-and-warnings">4.3 Errors and Warnings</a></h2>
<h1>5 Prepare to Use a Boost Library Binary</h1>
<p>If you want to use any of the separately-compiled Boost libraries, you'll need to acquire library binaries.</p>
<h2>5.1 Simplified Build From Source</h2>
<p>If you wish to build from source with Visual C++, you can use a simple build procedure described in this section. Open the command prompt and change your current directory to the Boost root directory. Then, type the following commands:</p>
<div class="highlight"><pre><span></span>bootstrap
.<span class="se">\b</span><span class="m">2</span>
</pre></div>
<p>The first command prepares the Boost.Build system for use. The second command invokes Boost.Build to build the separately-compiled Boost libraries. Please consult the <a href="https://www.boost.org/build/doc/html/bbv2/overview/invocation.html">Boost.Build documentation</a> for a list of allowed options.</p>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#or-build-binaries-from-source">5.2 Or,Build Binary From Source</a></h2>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#expected-build-output">5.3 Expected Build Output</a></h2>
<h2><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html#in-case-of-build-errors">5.4 In Case of Buid Errors</a></h2>
<h1>6 Link Your Program to a Boost Library</h1>
<p>To demonstrate linking with a Boost binary library, we'll use the following simple program that extracts the subject lines from emails. It uses the <a href="https://www.boost.org/doc/libs/1_68_0/libs/regex/index.html">Boost.Regex</a> library, which has a separately-compiled binary component.</p>
<div class="highlight"><pre><span></span><span class="cp">#include</span> <span class="cpf"><boost/regex.hpp></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><iostream></span><span class="cp"></span>
<span class="cp">#include</span> <span class="cpf"><string></span><span class="cp"></span>
<span class="kt">int</span> <span class="nf">main</span><span class="p">()</span>
<span class="p">{</span>
<span class="n">std</span><span class="o">::</span><span class="n">string</span> <span class="n">line</span><span class="p">;</span>
<span class="n">boost</span><span class="o">::</span><span class="n">regex</span> <span class="n">pat</span><span class="p">(</span> <span class="s">"^Subject: (Re: |Aw: )*(.*)"</span> <span class="p">);</span>
<span class="k">while</span> <span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">cin</span><span class="p">)</span>
<span class="p">{</span>
<span class="n">std</span><span class="o">::</span><span class="n">getline</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">cin</span><span class="p">,</span> <span class="n">line</span><span class="p">);</span>
<span class="n">boost</span><span class="o">::</span><span class="n">smatch</span> <span class="n">matches</span><span class="p">;</span>
<span class="k">if</span> <span class="p">(</span><span class="n">boost</span><span class="o">::</span><span class="n">regex_match</span><span class="p">(</span><span class="n">line</span><span class="p">,</span> <span class="n">matches</span><span class="p">,</span> <span class="n">pat</span><span class="p">))</span>
<span class="n">std</span><span class="o">::</span><span class="n">cout</span> <span class="o"><<</span> <span class="n">matches</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span> <span class="o"><<</span> <span class="n">std</span><span class="o">::</span><span class="n">endl</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">}</span>
</pre></div>
<p>There are two main challenges associated with linking:</p>
<ol>
<li>Tool configuration, e.g. choosing command-line options or IDE build settings.</li>
<li>Identifying the library binary, among all the build variants, whose compile configuration is compatible with the rest of your project.</li>
</ol>
<blockquote>
<p><strong>Auto-Linking</strong></p>
<p>Most Windows compilers and linkers have so-called “auto-linking support,” which eliminates the second challenge. Special code in Boost header files detects your compiler options and uses that information to encode the name of the correct library into your object files; the linker selects the library with that name from the directories you've told it to search.
The GCC toolchains (Cygwin and MinGW) are notable exceptions; GCC users should refer to the <a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/unix-variants.html#link-your-program-to-a-boost-library">linking instructions for Unix variant OSes</a> for the appropriate command-line options to use.</p>
</blockquote>
<h2>6.1 Link From Within the Visual Studio IDE</h2>
<p>Starting with the <em>header-only example project</em> we created earlier:</p>
<ol>
<li>Right-click <strong>example</strong> in the Solution Explorer pane and select Properties from the resulting pop-up menu.</li>
<li>In Configuration <em>Properties > Linker > Additional Library Directories</em>, enter the path to the Boost binaries, e.g. <em>C:\Program Files\boost\boost_1_67_0\lib\</em>.</li>
<li>From the <em>Build</em> menu, select <em>Build Solution</em>.</li>
</ol>
<h2>6.2 Or,Link From the Command Prompt</h2>
<p>For example, we can compile and link the above program from the Visual C++ command-line by simply adding the <strong>bold</strong> text below to the command line we used earlier, assuming your Boost binaries are in <em>C:\Program Files\boost\boost_1_67_0\lib</em>:</p>
<div class="highlight"><pre><span></span><span class="n">cl</span> <span class="o">/</span><span class="n">EHsc</span> <span class="o">/</span><span class="n">I</span> <span class="n">path</span><span class="err">\</span><span class="k">to</span><span class="err">\</span><span class="n">boost_1_67_0</span> <span class="n">example</span><span class="p">.</span><span class="n">cpp</span> <span class="o">/</span><span class="n">link</span> <span class="o">/</span><span class="n">LIBPATH</span><span class="p">:</span><span class="k">C</span><span class="p">:</span><span class="err">\</span><span class="n">Program</span> <span class="n">Files</span><span class="err">\</span><span class="n">boost</span><span class="err">\</span><span class="n">boost_1_67_0</span><span class="err">\</span><span class="n">lib</span>
</pre></div>
<h2>6.3 Library Naming</h2>
<blockquote>
<p><strong>Note</strong></p>
<p>If, like Visual C++, your compiler supports auto-linking, you can probably skip to the next step.</p>
</blockquote>
<p>In order to choose the right binary for your build configuration you need to know how Boost binaries are named. Each library filename is composed of a common sequence of elements that describe how it was built. For example, <code>libboost_regex-vc71-mt-d-x86-1_34.lib</code> can be broken down into the following elements:</p>
<p><strong>lib</strong>
Prefix: except on Microsoft Windows, every Boost library name begins with this string. On Windows, only ordinary static libraries use the lib prefix; import libraries and DLLs do not.</p>
<p><strong>boost_regex</strong>
Library name: all boost library filenames begin with boost_.</p>
<p><strong>-vc71</strong>
Toolset tag: identifies the toolset and version used to build the binary.</p>
<p><strong>-mt</strong>
Threading tag: indicates that the library was built with multithreading support enabled. Libraries built without multithreading support can be identified by the absence of <code>-mt</code>.</p>
<p><strong>-d</strong>
ABI tag: encodes details that affect the library's interoperability with other compiled code. For each such feature, a single letter is added to the tag:</p>
<blockquote>
<table>
<thead>
<tr>
<th>Key</th>
<th>Use this library when:</th>
<th>Boost.Build option</th>
</tr>
</thead>
<tbody>
<tr>
<td>s</td>
<td>linking statically to the C++ standard library and compiler runtime support libraries.</td>
<td>runtime-link=static</td>
</tr>
<tr>
<td>g</td>
<td>using debug versions of the standard and runtime support libraries.</td>
<td>runtime-debugging=on</td>
</tr>
<tr>
<td>y</td>
<td>using a special <a href="https://www.boost.org/doc/libs/1_68_0/libs/python/doc/html/building/python_debugging_builds.html">debug build of Python</a>.</td>
<td>python-debugging=on</td>
</tr>
<tr>
<td>d</td>
<td>building a debug version of your code.</td>
<td>variant=debug</td>
</tr>
<tr>
<td>p</td>
<td>using the STLPort standard library rather than the default one supplied with your compiler.</td>
<td>stdlib=stlport</td>
</tr>
</tbody>
</table>
<p>For example, if you build a debug version of your code for use with debug versions of the static runtime library and the STLPort standard library, the tag would be: -sgdp. If none of the above apply, the ABI tag is ommitted.</p>
</blockquote>
<p><strong>-x86</strong>
Architecture and address model tag: in the first letter, encodes the architecture as follows:</p>
<blockquote>
<table>
<thead>
<tr>
<th>Key</th>
<th>Architecture</th>
<th>Boost.Build option</th>
</tr>
</thead>
<tbody>
<tr>
<td>x</td>
<td>x85-32,x86-64</td>
<td>architecture=x86</td>
</tr>
<tr>
<td>a</td>
<td>ARM</td>
<td>architecture=arm</td>
</tr>
<tr>
<td>i</td>
<td>IA-64</td>
<td>architecture=ia64</td>
</tr>
<tr>
<td>s</td>
<td>Sparc</td>
<td>architecture=sparc</td>
</tr>
<tr>
<td>m</td>
<td>MIPS/SGI</td>
<td>architecture=mips*</td>
</tr>
<tr>
<td>p</td>
<td>RS/6000 & PowerPC</td>
<td>architecture=power</td>
</tr>
</tbody>
</table>
<p>The two digits following the letter encode the address model an follows:</p>
<table>
<thead>
<tr>
<th>Key</th>
<th>Address model</th>
<th>Boost.Build option</th>
</tr>
</thead>
<tbody>
<tr>
<td>32</td>
<td>32 bit</td>
<td>address-model=32</td>
</tr>
<tr>
<td>64</td>
<td>64 bit</td>
<td>address-model=64</td>
</tr>
</tbody>
</table>
</blockquote>
<p><strong>-1_34</strong>
Version tag: the full Boost release number, with periods replaced by underscores. For example, version <em>1.31.1</em> would be tagged as "<em>-1_31_1</em>".</p>
<p><strong>.lib</strong>
Extension: determined according to the operating system's usual convention. On most unix-style platforms the extensions are <code>.a</code> and <code>.so</code> for static libraries (archives) and shared libraries, respectively. On Windows, <code>.dll</code> indicates a shared library and .lib indicates a static or import library. Where supported by toolsets on unix variants, a full version extension is added (e.g. "<em>.so.1.34</em>") and a symbolic link to the library file, named without the trailing version number, will also be created.</p>
<h2>6.4 Test Your Program</h2>
<p>To test our subject extraction, we'll filter the following text file. Copy it out of your browser and save it as <strong>jayne.txt</strong>:</p>
<div class="highlight"><pre><span></span><span class="n">To</span><span class="o">:</span> <span class="n">George</span> <span class="n">Shmidlap</span>
<span class="n">From</span><span class="o">:</span> <span class="n">Rita</span> <span class="n">Marlowe</span>
<span class="n">Subject</span><span class="o">:</span> <span class="n">Will</span> <span class="n">Success</span> <span class="n">Spoil</span> <span class="n">Rock</span> <span class="n">Hunter</span><span class="o">?</span>
<span class="o">---</span>
<span class="n">See</span> <span class="n">subject</span><span class="o">.</span>
</pre></div>
<p>Now, in a command prompt window, type:</p>
<div class="highlight"><pre><span></span><span class="n">path</span><span class="err">\</span><span class="k">to</span><span class="err">\</span><span class="n">compiled</span><span class="err">\</span><span class="n">example</span> <span class="o"><</span> <span class="n">path</span><span class="err">\</span><span class="k">to</span><span class="err">\</span><span class="n">jayne</span><span class="p">.</span><span class="n">txt</span>
</pre></div>
<p>The program should respond with the email subject, “Will Success Spoil Rock Hunter?”</p>
<h1>7 Conclusion and Further Resources</h1>
<p>This concludes your introduction to Boost and to integrating it with your programs. As you start using Boost in earnest, there are surely a few additional points you'll wish we had covered. One day we may have a “Book 2 in the Getting Started series” that addresses them. Until then, we suggest you pursue the following resources. If you can't find what you need, or there's anything we can do to make this document clearer, please post it to the <a href="https://www.boost.org/more/mailing_lists.htm#users">Boost Users' mailing list</a>.</p>
<ul>
<li><a href="https://www.boost.org/doc/libs/1_68_0/tools/build/index.html">Boost.Build reference manual</a></li>
<li><a href="https://www.boost.org/more/mailing_lists.htm#users">Boost Users' mailing list</a></li>
<li><a href="https://www.boost.org/more/mailing_lists.htm#jamboost">Boost.Build mailing list</a></li>
<li><a href="https://www.boost.org/doc/libs/1_68_0/libs/index.html">Index of all Boost library documentation</a></li>
</ul>
<blockquote>
<p><strong>Onward</strong></p>
<p>Good luck, and have fun!</p>
<p>—the Boost Developers</p>
</blockquote>
<h1><a href="https://www.boost.org/doc/libs/1_68_0/more/getting_started/windows.html">Orign page</a></h1>try pelican2018-11-12T00:00:00+08:002018-11-12T00:00:00+08:00fx-moontag:www.git.moe,2018-11-12:/try-pelican.html<h1>try pelican</h1>
<blockquote>
<p>I just forget the usage again and again,so I decided to WcRoIpTyE it=.=</p>
</blockquote>
<h1>getting start</h1>
<h2>installing</h2>
<p>Pelican currently runs best on Python 2.7.x and 3.3+; earlier versions of Python are not supported.</p>
<p>You can install Pelican via several different methods. The simplest is via …</p><h1>try pelican</h1>
<blockquote>
<p>I just forget the usage again and again,so I decided to WcRoIpTyE it=.=</p>
</blockquote>
<h1>getting start</h1>
<h2>installing</h2>
<p>Pelican currently runs best on Python 2.7.x and 3.3+; earlier versions of Python are not supported.</p>
<p>You can install Pelican via several different methods. The simplest is via pip:</p>
<div class="highlight"><pre><span></span><span class="n">pip</span> <span class="n">install</span> <span class="n">pelican</span>
</pre></div>
<p>If you plan on using Markdown as a markup format, you’ll need to install the Markdown library:</p>
<div class="highlight"><pre><span></span><span class="n">pip</span> <span class="n">install</span> <span class="n">markdown</span>
</pre></div>
<p>Typographical enhancements can be enabled in your settings file, but first the requisite Typogrify library must be installed:</p>
<div class="highlight"><pre><span></span><span class="n">pip</span> <span class="n">install</span> <span class="n">typogrify</span>
</pre></div>
<h2>upgrading</h2>
<div class="highlight"><pre><span></span><span class="n">pip</span> <span class="n">install</span> <span class="c1">--upgrade pelican</span>
</pre></div>
<h2>kickstart your site</h2>
<div class="highlight"><pre><span></span><span class="n">pelican</span><span class="o">-</span><span class="n">quickstart</span>
</pre></div>
<div class="highlight"><pre><span></span><span class="n">yourproject</span><span class="o">/</span>
<span class="err">├──</span> <span class="n">content</span>
<span class="err">│</span> <span class="err">└──</span> <span class="p">(</span><span class="n">pages</span><span class="p">)</span>
<span class="err">├──</span> <span class="k">output</span>
<span class="err">├──</span> <span class="n">develop_server</span><span class="p">.</span><span class="n">sh</span>
<span class="err">├──</span> <span class="n">fabfile</span><span class="p">.</span><span class="n">py</span>
<span class="err">├──</span> <span class="n">Makefile</span>
<span class="err">├──</span> <span class="n">pelicanconf</span><span class="p">.</span><span class="n">py</span> <span class="o">#</span> <span class="n">Main</span> <span class="n">settings</span> <span class="n">file</span>
<span class="err">└──</span> <span class="n">publishconf</span><span class="p">.</span><span class="n">py</span> <span class="o">#</span> <span class="n">Settings</span> <span class="k">to</span> <span class="n">use</span> <span class="k">when</span> <span class="n">ready</span> <span class="k">to</span> <span class="n">publish</span>
</pre></div>
<h1>writing content</h1>
<h2>articles and pages</h2>
<p>Pelican considers “articles” to be chronological content, such as posts on a blog, and thus associated with a date.</p>
<p>The idea behind “pages” is that they are usually not temporal in nature and are used for content that does not change very often.</p>
<h2>file metadata</h2>
<p>Pelican tries to be smart enough to get the information it needs from the file system (for instance, about the category of your articles), but some information you need to provide in the form of metadata inside your files.</p>
<p>Metadata syntax for Markdown posts should follow this pattern:</p>
<div class="highlight"><pre><span></span><span class="nv">Title</span>: <span class="nv">My</span> <span class="nv">super</span> <span class="nv">title</span>
<span class="nv">Date</span>: <span class="mi">2010</span><span class="o">-</span><span class="mi">12</span><span class="o">-</span><span class="mi">03</span> <span class="mi">10</span>:<span class="mi">20</span>
<span class="nv">Modified</span>: <span class="mi">2010</span><span class="o">-</span><span class="mi">12</span><span class="o">-</span><span class="mi">05</span> <span class="mi">19</span>:<span class="mi">30</span>
<span class="nv">Category</span>: <span class="nv">Python</span>
<span class="nv">Tags</span>: <span class="nv">pelican</span>, <span class="nv">publishing</span>
<span class="nv">Slug</span>: <span class="nv">my</span><span class="o">-</span><span class="nv">super</span><span class="o">-</span><span class="nv">post</span>
<span class="nv">Authors</span>: <span class="nv">Alexis</span> <span class="nv">Metaireau</span>, <span class="nv">Conan</span> <span class="nv">Doyle</span>
<span class="nv">Summary</span>: <span class="nv">Short</span> <span class="nv">version</span> <span class="k">for</span> <span class="nv">index</span> <span class="nv">and</span> <span class="nv">feeds</span>
<span class="nv">This</span> <span class="nv">is</span> <span class="nv">the</span> <span class="nv">content</span> <span class="nv">of</span> <span class="nv">my</span> <span class="nv">super</span> <span class="nv">blog</span> <span class="nv">post</span>.
</pre></div>
<h2>pages</h2>
<p>If you create a folder named <code>pages</code> inside the content folder, all the files in it will be used to generate static pages, such as About or Contact pages. (See example filesystem layout below.)</p>
<p>You can use the <code>DISPLAY_PAGES_ON_MENU</code> setting to control whether all those pages are displayed in the primary navigation menu. (Default is <code>True</code>.)</p>
<p>If you want to exclude any pages from being linked to or listed in the menu then add a <code>status: hidden</code> attribute to its metadata. This is useful for things like making error pages that fit the generated theme of your site.</p>
<h2>linking to internal content</h2>
<div class="highlight"><pre><span></span><span class="n">it</span><span class="err">'</span><span class="n">s</span> <span class="n">useful</span> <span class="n">i</span> <span class="n">think</span>
</pre></div>
<p>From Pelican 3.1 onwards, it is now possible to specify intra-site links to files in the <em>source</em> content hierarchy instead of files in the <em>generated</em> hierarchy. This makes it easier to link from the current post to other content that may be sitting alongside that post (instead of having to determine where the other content will be placed after site generation).</p>
<p>To link to internal content (files in the <code>content</code> directory), use the following syntax for the link target: <code>{filename}path/to/file</code> Note: forward slashes, <code>/</code>, are the required path separator in the <code>{filename}</code> directive on all operating systems, including Windows.</p>
<h3>linking to static files</h3>
<p>Linking to non-article or non-page content uses the same <code>{filename}</code> syntax as described above. It is important to remember that those files will not be copied to the output directory unless the source directories containing them are included in the <code>STATIC_PATHS</code> setting of the project’s <code>pelicanconf.py</code> file. Pelican’s default configuration includes the <code>images</code> directory for this, but others must be added manually. Forgetting to do so will result in broken links.</p>
<h3>mixed content in the same directory</h3>
<p>Starting with Pelican 3.5, static files can safely share a source directory with page source files, without exposing the page sources in the generated site. Any such directory must be added to both <code>STATIC_PATHS</code> and <code>PAGE_PATHS</code> (or <code>STATIC_PATHS</code> and <code>ARTICLE_PATHS</code>). Pelican will identify and process the page source files normally, and copy the remaining files as if they lived in a separate directory reserved for static files.</p>
<p>Note: Placing static and content source files together in the same source directory does not guarantee that they will end up in the same place in the generated site. The easiest way to do this is by using the <code>{attach}</code> link syntax (described below). Alternatively, the <code>STATIC_SAVE_AS</code>, <code>PAGE_SAVE_AS</code>, and <code>ARTICLE_SAVE_AS</code> settings (and the corresponding <code>*_URL</code> settings) can be configured to place files of different types together, just as they could in earlier versions of Pelican.</p>
<h3>attaching static files</h3>
<p>Starting with Pelican 3.5, static files can be “attached” to a page or article using this syntax for the link target: <code>{attach}path/to/file</code> This works like the <code>{filename}</code> syntax, but also relocates the static file into the linking document’s output directory. If the static file originates from a subdirectory beneath the linking document’s source, that relationship will be preserved on output. Otherwise, it will become a sibling of the linking document.</p>
<p>This only works for linking to static files, and only when they originate from a directory included in the <code>STATIC_PATHS</code> setting.</p>
<h3>linking to authors,categories,index and tags</h3>
<p>You can link to authors, categories, index and tags using the <code>{author}name</code>, <code>{category}foobar</code>, <code>{index}</code> and <code>{tag}tagname</code> syntax.</p>
<h3>deprecated internal link syntax</h3>
<p>To remain compatible with earlier versions, Pelican still supports vertical bars (<code>||</code>) in addition to curly braces (<code>{}</code>) for internal links. For example: <code>|filename|an_article.rst</code>, <code>|tag|tagname</code>, <code>|category|foobar</code>. The syntax was changed from <code>||</code> to <code>{}</code> to avoid collision with Markdown extensions or reST directives. Support for the old syntax may eventually be removed.</p>
<h2>importing an existing site</h2>
<p>It is possible to import your site from WordPress, Tumblr, Dotclear, and RSS feeds using a simple script. See <a href="http://docs.getpelican.com/en/stable/importer.html#import"><code>Importing an existing site</code></a>.</p>
<h2>translations</h2>
<h2>syntax highlighting</h2>
<h2>publishing drafts</h2>
<h1>publish your site</h1>
<h2>site generation</h2>
<p>Once Pelican is installed and you have some content (e.g., in Markdown or reST format), you can convert your content into HTML via the <code>pelican</code> command, specifying the path to your content and (optionally) the path to your <a href="http://docs.getpelican.com/en/stable/settings.html">settings</a> file:</p>
<div class="highlight"><pre><span></span><span class="n">pelican</span> <span class="o">/</span><span class="n">path</span><span class="o">/</span><span class="k">to</span><span class="o">/</span><span class="n">your</span><span class="o">/</span><span class="n">content</span><span class="o">/</span> <span class="p">[</span><span class="o">-</span><span class="n">s</span> <span class="n">path</span><span class="o">/</span><span class="k">to</span><span class="o">/</span><span class="n">your</span><span class="o">/</span><span class="n">settings</span><span class="p">.</span><span class="n">py</span><span class="p">]</span>
</pre></div>
<p>The above command will generate your site and save it in the <code>output/</code> folder, using the default theme to produce a simple site. The default theme consists of very simple <strong>HTML</strong> without styling and is provided so folks may use it as a basis for creating their own themes.</p>
<p>When working on a single article or page, it is possible to generate only the file that corresponds to that content. To do this, use the <code>--write-selected</code> argument, like so:</p>
<div class="highlight"><pre><span></span><span class="n">pelican</span> <span class="c1">--write-selected output/posts/my-post-title.html</span>
</pre></div>
<p>Note that you must specify the path to the generated output file — not the source content. To determine the output file name and location, use the <code>--debug</code> flag. If desired, <code>--write-selected</code> can take a comma-separated list of paths or can be configured as a setting. (See: <a href="http://docs.getpelican.com/en/stable/settings.html#writing-only-selected-content">Writing only selected content</a>)</p>
<p>Pelican has other command-line switches available. Have a look at the help to see all the options you can use:</p>
<div class="highlight"><pre><span></span><span class="n">pelican</span> <span class="c1">--help</span>
</pre></div>
<h3>viewing the generated files</h3>
<p>The files generated by Pelican are static files, so you don’t actually need anything special to view them. You can use your browser to open the generated HTML files directly:</p>
<div class="highlight"><pre><span></span><span class="n">firefox</span> <span class="k">output</span><span class="o">/</span><span class="k">index</span><span class="p">.</span><span class="n">html</span>
</pre></div>
<p>Because the above method may have trouble locating your CSS and other linked assets, running a simple web server using Python will often provide a more reliable previewing experience.</p>
<p>For Python 2, run:</p>
<div class="highlight"><pre><span></span><span class="n">cd</span> <span class="k">output</span>
<span class="n">python</span> <span class="o">-</span><span class="n">m</span> <span class="n">SimpleHTTPServer</span>
</pre></div>
<p>For Python 3,run:</p>
<div class="highlight"><pre><span></span><span class="n">cd</span> <span class="k">output</span>
<span class="n">python</span> <span class="o">-</span><span class="n">m</span> <span class="n">http</span><span class="p">.</span><span class="n">server</span>
</pre></div>
<p>Once the basic server has been started, you can preview your site at <a href="http://localhost:8000/">http://localhost:8000/</a></p>
<h2>deployment</h2>
<p>After you have generated your site, previewed it in your local development environment, and are ready to deploy it to production, you might first re-generate your site with any production-specific settings (e.g., analytics feeds, etc.) that you may have defined:</p>
<div class="highlight"><pre><span></span><span class="n">pelican</span> <span class="n">content</span> <span class="o">-</span><span class="n">s</span> <span class="n">publishconf</span><span class="p">.</span><span class="n">py</span>
</pre></div>
<p>To base your publish configuration on top of your <code>pelicanconf.py</code>, you can import your pelicanconf settings by including the following line in your <code>publishconf.py</code>:</p>
<div class="highlight"><pre><span></span><span class="kn">from</span> <span class="nn">pelicanconf</span> <span class="kn">import</span> <span class="o">*</span>
</pre></div>
<p>If you have generated a <code>publishconf.py</code> using <code>pelican-quickstart</code>, this line is included by default.</p>
<p>The steps for deploying your site will depend on where it will be hosted. If you have SSH access to a server running Nginx or Apache, you might use the <code>rsync</code> tool to transmit your site files:</p>
<div class="highlight"><pre><span></span>rsync -avc --delete output/ host.example.com:/var/www/your-site/
</pre></div>
<p>There are many other deployment options, some of which can be configured when first setting up your site via the <code>pelican-quickstart</code> command. See the <a href="http://docs.getpelican.com/en/stable/tips.html">Tips</a> page for detail on publishing via GitHub Pages.</p>
<h2>automation</h2>
<p>While the <code>pelican</code> command is the canonical way to generate your site, automation tools can be used to streamline the generation and publication flow. One of the questions asked during the <code>pelican-quickstart</code> process pertains to whether you want to automate site generation and publication. If you answered “<em>yes</em>” to that question, a <code>tasks.py</code> and <code>Makefile</code> will be generated in the root of your project. These files, pre-populated with certain information gleaned from other answers provided during the pelican-quickstart process, are meant as a starting point and should be customized to fit your particular needs and usage patterns. If you find one or both of these automation tools to be of limited utility, these files can deleted at any time and will not affect usage of the canonical pelican command.</p>
<p>Following are automation tools that “wrap” the <code>pelican</code> command and can simplify the process of generating, previewing, and uploading your site.</p>
<h3>invoke</h3>
<p>The advantage of <a href="http://www.pyinvoke.org/">Invoke</a> is that it is written in Python and thus can be used in a wide range of environments. The downside is that it must be installed separately. Use the following command to install Invoke, prefixing with <code>sudo</code> if your environment requires it:</p>
<div class="highlight"><pre><span></span><span class="n">pip</span> <span class="n">install</span> <span class="n">invoke</span>
</pre></div>
<p>Take a moment to open the <code>tasks.py</code> file that was generated in your project root. You will see a number of commands, any one of which can be renamed, removed, and/or customized to your liking. Using the out-of-the-box configuration, you can generate your site via:</p>
<div class="highlight"><pre><span></span><span class="n">invoke</span> <span class="n">build</span>
</pre></div>
<p>If you’d prefer to have Pelican automatically regenerate your site every time a change is detected (which is handy when testing locally), use the following command instead:</p>
<div class="highlight"><pre><span></span><span class="n">invoke</span> <span class="n">regenerate</span>
</pre></div>
<p>To serve the generated site so it can be previewed in your browser at <a href="http://localhost:8000/">http://localhost:8000/</a>:</p>
<div class="highlight"><pre><span></span><span class="n">invoke</span> <span class="n">serve</span>
</pre></div>
<p>If during the <code>pelican-quickstart</code> process you answered “<em>yes</em>” when asked whether you want to upload your site via SSH, you can use the following command to publish your site via rsync over SSH:</p>
<div class="highlight"><pre><span></span><span class="n">invoke</span> <span class="n">publish</span>
</pre></div>
<p>These are just a few of the commands available by default, so feel free to explore <code>tasks.py</code> and see what other commands are available. More importantly, don’t hesitate to customize <code>tasks.py</code> to suit your specific needs and preferences.</p>
<h3>make</h3>
<p>A <code>Makefile</code> is also automatically created for you when you say “yes” to the relevant question during the <code>pelican-quickstart</code> process. The advantage of this method is that the <code>make</code> command is built into most POSIX systems and thus doesn’t require installing anything else in order to use it. The downside is that non-POSIX systems (e.g., Windows) do not include <code>make</code>, and installing it on those systems can be a non-trivial task.</p>
<p>If you want to use <code>make</code> to generate your site using the settings in <code>pelicanconf.py</code>, run:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">html</span>
</pre></div>
<p>To generate the site for production, using the settings in <code>publishconf.py</code>, run:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">publish</span>
</pre></div>
<p>If you’d prefer to have Pelican automatically regenerate your site every time a change is detected (which is handy when testing locally), use the following command instead:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">regenerate</span>
</pre></div>
<p>To serve the generated site so it can be previewed in your browser at <a href="http://localhost:8000/">http://localhost:8000/</a>:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">serve</span>
</pre></div>
<p>Normally you would need to run <code>make regenerate</code> and <code>make serve</code> in two separate terminal sessions, but you can run both at once via:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">devserver</span>
</pre></div>
<p>The above command will simultaneously run Pelican in regeneration mode as well as serve the output at <a href="http://localhost:8000">http://localhost:8000</a>.</p>
<p>When you’re ready to publish your site, you can upload it via the method(s) you chose during the <code>pelican-quickstart</code> questionnaire. For this example, we’ll use rsync over ssh:</p>
<div class="highlight"><pre><span></span><span class="n">make</span> <span class="n">rsync_upload</span>
</pre></div>
<p>(The default <code>Makefile</code> and <code>devserver.sh</code> scripts use the <code>python</code> and <code>pelican</code> executables to complete its tasks. If you want to use different executables, such as <code>python3</code>, you can set the <code>PY</code> and <code>PELICAN</code> environment variables, respectively, to override the default executable names.)</p>git learning note2018-08-10T00:00:00+08:002018-08-10T00:00:00+08:00fx-moontag:www.git.moe,2018-08-10:/git-learning-note.html<h1>git learning note</h1>
<hr>
<h2>git init</h2>
<p>This creates a new subdirectory named .git that contains all of your necessary repository files — a Git repository skeleton. At this point, nothing in your project is tracked yet. </p>
<h2>git add</h2>
<p>If you want to start version-controlling existing files (as opposed to an empty directory …</p><h1>git learning note</h1>
<hr>
<h2>git init</h2>
<p>This creates a new subdirectory named .git that contains all of your necessary repository files — a Git repository skeleton. At this point, nothing in your project is tracked yet. </p>
<h2>git add</h2>
<p>If you want to start version-controlling existing files (as opposed to an empty directory), you should probably begin tracking those files and do an initial commit.</p>
<h2>git commit</h2>
<p>You can accomplish that with a few git add commands that specify the files you want to track, followed by a <code>git commit</code>.</p>
<h2>git clone</h2>
<p>If you want to get a copy of an existing Git repository — for example, a project you’d like to contribute to — the command you need is <code>git clone</code>.</p>
<h2>git status</h2>
<p>The main tool you use to determine which files are in which state.</p>
<blockquote>
<p>nothing to commit, working directory clean</p>
</blockquote>
<p>This means you have a clean working directory — in other words, none of your tracked files are modified. Git also doesn’t see any untracked files, or they would be listed here.</p>
<h3>short status</h3>
<p>While the <code>git status</code> output is pretty comprehensive, it’s also quite wordy. Git also has a short status flag so you can see your changes in a more compact way. If you run <code>git status -s</code> or <code>git status --short</code> you get a far more simplified output from the command.</p>
<h2>Ignoring Files</h2>
<p>Often, you’ll have a class of files that you don’t want Git to automatically add or even show you as being untracked. These are generally automatically generated files such as log files or files produced by your build system. In such cases, you can create a file listing patterns to match them named <code>.gitignore</code>.</p>
<h2>git diff</h2>
<p>If the <code>git status</code> command is too vague for you — you want to know exactly what you changed, not just which files were changed — you can use the <code>git diff</code> command.</p>
<h2>git rm</h2>
<p>To remove a file from Git, you have to remove it from your tracked files (more accurately, remove it from your staging area) and then commit. The <code>git rm</code> command does that, and also removes the file from your working directory so you don’t see it as an untracked file the next time around.</p>
<h2>git mv</h2>
<p>Thus it’s a bit confusing that Git has a mv command. If you want to rename a file in Git, you can run something like:</p>
<p><code>$ git mv file_from file_to</code></p>
<p>and it works fine.</p>
<h2>git log</h2>
<p>After you have created several commits, or if you have cloned a repository with an existing commit history, you’ll probably want to look back to see what has happened. The most basic and powerful tool to do this is the <code>git log</code> command.</p>
<p>One of the more helpful options is <code>-p</code> or <code>--patch</code>, which shows the difference (the patch output) introduced in each commit. You can also limit the number of log entries displayed, such as using <code>-2</code> to show only the last two entries.</p>
<p>If you want to see some abbreviated stats for each commit, you can use the <code>--stat</code> option</p>