I think ... - pythonhttps://blog.kmonsoor.com/2018-07-07T00:00:00+06:00Install latest Python 3 on Linux CentOS 72018-07-07T00:00:00+06:002018-07-07T00:00:00+06:00Khaled Monsoortag:blog.kmonsoor.com,2018-07-07:/install-latest-python3-on-centos-7/<p>Install the latest and greatest Python 3 on CentOS 7 systems</p><h2 id="why">Why<a class="headerlink" href="#why" title="Permanent link">¶</a></h2>
<p>Not all distro created equal. <br>
Some are created to join the space race, some are to hold unto the leagcy, some are cutting-edge, some are cutting edge. Some are born to boot-up IoT devices some are to push out heavy graphics.</p>
<p>That’s the fun (albeit, power) of Linux.</p>
<p><img alt="CentOS 7 logo" class="noZoom" src="https://i.imgur.com/6ZFCdoM.jpg"></p>
<p>CentOS 7 is a powerful and stable distro that runs on thousands (probably, millions) production-grade servers.<br>
In the matter of stability, it’s a beast. However, it doesn’t ship with Python 3, by default. You can install it via <span class="caps">EPEL</span> repository, or the below simple steps.</p>
<p>Also, take a note. The Python <strong>2</strong> comes with the system, which is probably 2.7.5, do <strong><span class="caps">NOT</span></strong> mess with it. Many system components rely on that specific version. If you need the latest versions of 2, use <code>virtualenv</code> or <code>pipenv</code>.</p>
<h3 id="prepare-your-system">Prepare your system<a class="headerlink" href="#prepare-your-system" title="Permanent link">¶</a></h3>
<p>Start with installing pre-requisite utilities for compilation and development support.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ sudo yum update <span class="o">&&</span> sudo yum groupinstall -y <span class="s2">"development tools"</span>
<span class="linenos" data-linenos="2 "></span>$ sudo yum install -y zlib-devel bzip2-devel openssl-devel ncurses-devel <span class="se">\</span>
<span class="linenos" data-linenos="3 "></span> sqlite-devel readline-devel tk-devel gdbm-devel <span class="se">\</span>
<span class="linenos" data-linenos="4 "></span> db4-devel libpcap-devel xz-devel expat-devel
</code></pre></div>
<h3 id="download-latest-python-source-code-from-pythonorg">Download latest Python source code from Python.org<a class="headerlink" href="#download-latest-python-source-code-from-pythonorg" title="Permanent link">¶</a></h3>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ wget https://www.python.org/ftp/python/3.6.6/Python-3.6.6.tar.xz
<span class="linenos" data-linenos="2 "></span>$ tar xf Python-3.6.6.tar.xz
<span class="linenos" data-linenos="3 "></span>$ <span class="nb">cd</span> Python-3.6.6
</code></pre></div>
<h3 id="enable-performance-optimizations-optional-but-highly-recommended">Enable performance optimizations (optional, but highly recommended)<a class="headerlink" href="#enable-performance-optimizations-optional-but-highly-recommended" title="Permanent link">¶</a></h3>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ ./configure --prefix<span class="o">=</span>/usr/local --enable-shared <span class="nv">LDFLAGS</span><span class="o">=</span><span class="s2">"-Wl,-rpath /usr/local/lib"</span>
<span class="linenos" data-linenos="2 "></span>$ ./configure --enable-optimizations
</code></pre></div>
<h3 id="build-and-install">Build and install<a class="headerlink" href="#build-and-install" title="Permanent link">¶</a></h3>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ make
<span class="linenos" data-linenos="2 "></span>$ sudo make altinstall
</code></pre></div>
<p>Now, Python 3.6.6 is ready to be used in your system; located in <code>/usr/local/bin/python3.6</code>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ which python3.6
<span class="linenos" data-linenos="2 "></span>/usr/local/bin/python3.6
<span class="linenos" data-linenos="3 "></span>
<span class="linenos" data-linenos="4 "></span>$ python3.6
<span class="linenos" data-linenos="5 "></span>Python <span class="m">3</span>.6.6 <span class="o">(</span>default, Jul <span class="m">10</span> <span class="m">2018</span>, <span class="m">14</span>:04:26<span class="o">)</span>
<span class="linenos" data-linenos="6 "></span><span class="o">[</span>GCC <span class="m">4</span>.8.5 <span class="m">20150623</span> <span class="o">(</span>Red Hat <span class="m">4</span>.8.5-28<span class="o">)]</span> on linux
<span class="linenos" data-linenos="7 "></span>Type <span class="s2">"help"</span>, <span class="s2">"copyright"</span>, <span class="s2">"credits"</span> or <span class="s2">"license"</span> <span class="k">for</span> more information.
<span class="linenos" data-linenos="8 "></span>>>>
</code></pre></div></p>
<p>For convenience, you can create a symbolic-link with a shorter name.
If you had system-installed Python3 (unlikely), <strong>don’t</strong> do this, as some system-components may depend on that specific older version of Python 3.
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ sudo ln -s /usr/local/bin/python3.6 /usr/local/bin/python3
<span class="linenos" data-linenos="2 "></span>$ python3
<span class="linenos" data-linenos="3 "></span>Python <span class="m">3</span>.6.6 <span class="o">(</span>default, Jul <span class="m">10</span> <span class="m">2018</span>, <span class="m">14</span>:04:26<span class="o">)</span>
<span class="linenos" data-linenos="4 "></span><span class="o">[</span>GCC <span class="m">4</span>.8.5 <span class="m">20150623</span> <span class="o">(</span>Red Hat <span class="m">4</span>.8.5-28<span class="o">)]</span> on linux
<span class="linenos" data-linenos="5 "></span>Type <span class="s2">"help"</span>, <span class="s2">"copyright"</span>, <span class="s2">"credits"</span> or <span class="s2">"license"</span> <span class="k">for</span> more information.
<span class="linenos" data-linenos="6 "></span>>>>
</code></pre></div></p>
<h2 id="install-wheel-and-pip"><del>Install wheel and pip</del><a class="headerlink" href="#install-wheel-and-pip" title="Permanent link">¶</a></h2>
<p>You don’t need to, because <code>Python 3.6.6</code> includes these necessary tools included.
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ pip3.6 -V
<span class="linenos" data-linenos="2 "></span>pip <span class="m">10</span>.0.1 from /usr/local/lib/python3.6/site-packages/pip <span class="o">(</span>python <span class="m">3</span>.6<span class="o">)</span>
<span class="linenos" data-linenos="3 "></span>$ wheel version
<span class="linenos" data-linenos="4 "></span>wheel <span class="m">0</span>.29.0
</code></pre></div></p>Pelican Static sites - SEO Optimization2017-01-07T00:00:00+06:002017-01-07T00:00:00+06:00Khaled Monsoortag:blog.kmonsoor.com,2017-01-07:/pelican-how-to-make-seo-friendly/<p>Usually <code>Pelican</code> static-site generator is not very concerned about <span class="caps">SEO</span> of the generated site. Related themes and their templates also don’t take it much seriously. But you shouldn’t loose <span class="caps">SEO</span>, right?</p><p>Writing is a hard job, especially it is your hobby beside of your day job. But what’s the benefit if nobody reads it just because they couldn’t find it.</p>
<p>Usually <code>Pelican</code> <a href="https://github.com/getpelican/pelican">static-site generator</a> is not very concerned about <span class="caps">SEO</span> of the generated site mainly because it’s not that focused on commercial usage. That’s what I felt.
Related themes and their templates also don’t take it much seriously. But you shouldn’t loose <span class="caps">SEO</span> just because you migrated from Wordpress or whatever you were using previously, right?</p>
<p>Often times theme-authors focus more on look-n-feel of the theme, but not so much on the <span class="caps">SEO</span> concerns.</p>
<p>That’s this blog about; let’s fix that.</p>
<h4 id="note-1-about-other-static-site-generators">Note 1: About other static-site generators<a class="headerlink" href="#note-1-about-other-static-site-generators" title="Permanent link">¶</a></h4>
<p>Although the following discussions <span class="amp">&</span> codes mostly are specific to <a href="https://github.com/getpelican/pelican">Pelican</a> templates which uses <a href="http://jinja.pocoo.org/">jinja2</a> templating language, the concepts and concerns here are applicable to most static-site generators and their themes.</p>
<h4 id="note-2-im-in-no-way-an-seo-expert">Note 2: I’m, in no way, an <span class="caps">SEO</span> expert<a class="headerlink" href="#note-2-im-in-no-way-an-seo-expert" title="Permanent link">¶</a></h4>
<p>This writeup is just a collection of my findings while correcting my blog’s <span class="caps">SEO</span> course; fixing the stupid mistakes. Also, this isn’t a commercial site. There are lot more and in-depth aspects of <span class="caps">SEO</span> optimization other than the following, that can be very important for commercial projects.</p>
<h2 id="getting-started">Getting started<a class="headerlink" href="#getting-started" title="Permanent link">¶</a></h2>
<h3 id="lookup-for-missing-pieces">Lookup for missing pieces<a class="headerlink" href="#lookup-for-missing-pieces" title="Permanent link">¶</a></h3>
<p>Make sure all the linked resources(links, images, <span class="caps">CSS</span> <span class="amp">&</span> <span class="caps">JS</span> files) that you’ve used in your pages are valid. For that check browser’s <code>console</code> in <code>Developers tools</code> for any errors e.g. unavailable urls, faulty html/css etc.</p>
<h3 id="know-the-critical-spots">Know the critical spots<a class="headerlink" href="#know-the-critical-spots" title="Permanent link">¶</a></h3>
<ul>
<li><strong>pelicanconf.py</strong> - It’s usually in your root folder of the site.</li>
<li><strong>base.html</strong> - It’s in the <code>templates</code> folder of the theme folder that you are using. Changes here will impact all <span class="caps">HTML</span> pages generated by Pelican.</li>
<li><strong>article.html</strong> - In same folder as <code>base.html</code>. Changes here will impact only articles’ pages.</li>
</ul>
<h2 id="avoiding-duplication">Avoiding Duplication<a class="headerlink" href="#avoiding-duplication" title="Permanent link">¶</a></h2>
<h3 id="avoid-your-source-getting-indexed-by-google">Avoid your source getting indexed by Google<a class="headerlink" href="#avoid-your-source-getting-indexed-by-google" title="Permanent link">¶</a></h3>
<p>If the source of your blog is not sourced-open, meaning the content is not in a open-sourced repo, this isn’t your concern.
But if it is, it should be a concern. </p>
<p>The reason is that <code>Github.com</code>(or where your repo is hosted on) is stronger domain than yours, so Google “sees” that your site-contents (even though it’s yours) also is on Github. So, there’s a high chance that it’ll mark your contents as “duplicate”. And, duplicate contents gets heavy hammers from Google’s <span class="caps">SEO</span> point-of-view. Searching any writeup from yours, even it’s very unique on Internet, Google search will show both your site and the repo as well, possibly links from your site will be on the lower side.</p>
<p>It begs the question how to avoid that. It’s not complicated.</p>
<p>For example, Github.com’s <a href="https://github.com/robots.txt">robot.txt</a> allows Google (or any search engine for that matter) to index only the <code>master</code> branch of any open-source repo. So, if your repo don’t have any branch named <code>master</code>, it won’t be indexed. That’s it. Rename your “master” as “live”, “main”, “production” or whatever you feel like.</p>
<ol>
<li>Create a new “master”</li>
</ol>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ git checkout -b new-master
<span class="linenos" data-linenos="2 "></span>$ git push -u origin new-master
</code></pre></div>
<ol start="2">
<li>Tell Github about new move</li>
</ol>
<p><img alt="change repo-settings on Github" src="http://i.imgur.com/wjf6zwul.png"></p>
<ol start="3">
<li>Now, delete <code>master</code> branch from your repo.</li>
</ol>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>$ git branch -d master
<span class="linenos" data-linenos="2 "></span>$ git push origin :master
</code></pre></div>
<h3 id="utilize-relcanonical-link">Utilize <code>rel="canonical"</code> link<a class="headerlink" href="#utilize-relcanonical-link" title="Permanent link">¶</a></h3>
<p>This is kind of a must-do for avoiding being marked as duplicate content.
This will also defend you against automatic content-scraping schemes by always having a pointer to your original source. </p>
<p>To utilize it on Pelican, add or make sure that a <code><link></code> element with the attribute <code>rel="canonical"</code> to the <code><head></code> section of your base template named <code>base.html</code>.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>{% if article %}
<span class="linenos" data-linenos="2 "></span><link rel="canonical" href="{{ SITEURL }}/{{ article.url }}"/>
<span class="linenos" data-linenos="3 "></span>{% endif%}
</code></pre></div>
<p>For example, if you see this page’s source (pressing <span class="caps">CTRL</span>+u), you should see something like</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><link rel="canonical" href="https://blog.kmonsoor.com/pelican-how-to-make-seo-friendly/"/>
</code></pre></div>
<h3 id="proper-title-of-each-page">Proper <strong>< title ></strong> of each page<a class="headerlink" href="#proper-title-of-each-page" title="Permanent link">¶</a></h3>
<p>Every page on your site should have a proper title.
For search engines, it represents the page. It should concisely reflect a page’s content.
But try to keep it less 60 characters or search-engines may choose to truncate it. Use each characters wisely.</p>
<p>It may look like this in your <code>base.html</code>.</p>
<p><div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>{% if article %}
<span class="linenos" data-linenos="2 "></span><title>{{ article.title }} -- {{ TAGLINE }}</title>
<span class="linenos" data-linenos="3 "></span>{% else %}
<span class="linenos" data-linenos="4 "></span><title>{{ TAGLINE }}</title>
<span class="linenos" data-linenos="5 "></span>{% endif%}
</code></pre></div>
The <strong>else</strong> clause here is to ensure that non-article pages also get a title, even it’s just your <strong>tagline</strong> defined in <code>pelicanconf.py</code>.</p>
<h3 id="meta-descriptions">Meta descriptions<a class="headerlink" href="#meta-descriptions" title="Permanent link">¶</a></h3>
<p>Include a meta-description to be added on each page of your site.
Though it may don’t directly hit <span class="caps">SEO</span> ranking, but it appears as a snippet on the search page.
So, user should get a proper glimpse of what your page gonna talk about.
Make sure your theme uses Pelican’s <code>summary</code>-tagged text for this purpose. Else, ensure it yourself by editing <code>base.html</code>.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>{% if article and article.summary %}
<span class="linenos" data-linenos="2 "></span><meta name="description" content="{{ article.summary|striptags }}"/>
<span class="linenos" data-linenos="3 "></span>{% else %}
<span class="linenos" data-linenos="4 "></span><meta name="description" content="{{ SITE_SUMMARY }}"/>
<span class="linenos" data-linenos="5 "></span>{% endif%}
</code></pre></div>
<h3 id="use-search-console-extensively">Use <code>search-console</code> extensively<a class="headerlink" href="#use-search-console-extensively" title="Permanent link">¶</a></h3>
<p>Google’s <a href="https://www.google.com/webmasters/tools/home">Search-console, previously known as webmaster-tools</a> is your friend. Utilize it as far as you can go.</p>
<h4 id="extensively-use-pagespeed-insights">Extensively use <a href="https://developers.google.com/speed/pagespeed/insights/">PageSpeed Insights</a><a class="headerlink" href="#extensively-use-pagespeed-insights" title="Permanent link">¶</a></h4>
<p>To understand where are current bottlenecks of your site, this tools gives quite a lot insights. Address those one-by-one.</p>
<h4 id="set-preferred-version-of-your-site">Set preferred version of your site<a class="headerlink" href="#set-preferred-version-of-your-site" title="Permanent link">¶</a></h4>
<p>If you have <code>www</code>, <code>http</code> and <code>https</code> versions of your site, tell Google here which one is preferred. It’s only applicable to your domain-root. Once applied and Google re-indexed your site, all the search-results from your site will show that preferred version of your site.</p>
<p><img alt="setting preference for www or non-www version" src="http://i.imgur.com/51JY1oel.png"></p>
<p>You have to add and do it same both for <code>http</code> and <code>https</code> version of your site, if you have both.</p>
<p>If you have both, <strong>either</strong> you can use a javascript-code snippet in the <code><head></code> of <code>base.html</code> to redirect any <code>http</code> page to its <code>https</code> counterpart.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><script type="text/javascript">
<span class="linenos" data-linenos="2 "></span> var host = "your-site.com";
<span class="linenos" data-linenos="3 "></span> if ((host == window.location.host) && (window.location.protocol != "https:"))
<span class="linenos" data-linenos="4 "></span> window.location.protocol = "https";
<span class="linenos" data-linenos="5 "></span></script>
</code></pre></div>
<p><strong>or</strong>, if your site is served through <span class="caps">NGINX</span> or Apache, you can do it through site’s <code>.htaccess</code> file, by adding the following.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span>RewriteEngine On
<span class="linenos" data-linenos="2 "></span>RewriteCond %{HTTPS} !on
<span class="linenos" data-linenos="3 "></span>RewriteRule (.*) https://%{HTTP_HOST}%{REQUEST_URI}
</code></pre></div>
<p><strong>Or</strong>, if you are using CloudFlare <span class="caps">CDN</span>, you can create a page-rule for that as I have shown below.</p>
<p><img alt="always-https by CloudFlare page-rules" src="http://i.imgur.com/9ISFbtvm.png"></p>
<h4 id="check-index-status">Check index-status<a class="headerlink" href="#check-index-status" title="Permanent link">¶</a></h4>
<p>Once in a while Check for Google’s index status of your site on the <code>search-console</code>. Look for error messages or suggestions.</p>
<p>After every major change in your site’s structure, make sure Google bots “know” about it. You can somewhat expedite the process by <a href="https://www.google.com/webmasters/tools/submit-url">manually submitting</a> your site.</p>
<h3 id="include-opengraph-data">Include <code>OpenGraph</code> data<a class="headerlink" href="#include-opengraph-data" title="Permanent link">¶</a></h3>
<p>Make sure each of your pages is including proper <a href="http://ogp.me/">OpenGraph</a> tags, e.g. <code>og:title</code>, <code>og:content</code> etc., in your template.</p>
<p>Though, OpenGraph originated from facebook Inc., these tags are now widely used by other social engines, even by Google+. In absence of Twitter tags, Twitter also uses these <code>og</code> tags. Try to include both <code>og:</code> and <code>twitter:</code> tags. Proper data in these tags makes your article cleanly-sharable in these social sites.</p>
<p>The below snippet that <a href="https://github.com/kmonsoor/blog.kmonsoor.com/blob/pelican-how-to-make-seo-friendly/plumage/templates/base.html">I use myself</a> can serve as a starting point.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos=" 1 "></span><!-- OpenGraph protocol tags: http://ogp.me/ -->
<span class="linenos" data-linenos=" 2 "></span><!-- originally adopted to be used for: https://blog.kmonsoor.com -->
<span class="linenos" data-linenos=" 3 "></span><meta property="og:site_name" content="{{ SITENAME }}" />
<span class="linenos" data-linenos=" 4 "></span><meta property="og:type" content="article" />
<span class="linenos" data-linenos=" 5 "></span>{% if article and article.title %}
<span class="linenos" data-linenos=" 6 "></span><meta property="og:title" content="{{ article.title }} -- {{ TAGLINE }}" />
<span class="linenos" data-linenos=" 7 "></span><meta property="og:url" content="{{ SITEURL }}/{{ article.url }}" />
<span class="linenos" data-linenos=" 8 "></span>{% endif%}
<span class="linenos" data-linenos=" 9 "></span>{% if article and article.summary %}
<span class="linenos" data-linenos="10 "></span><meta property="og:description" content="{{ article.summary|striptags }}" />
<span class="linenos" data-linenos="11 "></span>{% else %}
<span class="linenos" data-linenos="12 "></span><meta name="og:description" content="{{ SITE_SUMMARY }}"/>
<span class="linenos" data-linenos="13 "></span>{% endif%}
<span class="linenos" data-linenos="14 "></span>{% if article and article.date %}
<span class="linenos" data-linenos="15 "></span><meta property="article:published_time" content="{{ article.date }}" />
<span class="linenos" data-linenos="16 "></span>{% endif%}
<span class="linenos" data-linenos="17 "></span>{% if article and article.modified %}
<span class="linenos" data-linenos="18 "></span><meta property="article:modified_time" content="{{ article.modified }}" />
<span class="linenos" data-linenos="19 "></span>{% endif%}
<span class="linenos" data-linenos="20 "></span><!-- End of OpenGraph protocol tags -->
<span class="linenos" data-linenos="21 "></span>
<span class="linenos" data-linenos="22 "></span>{% if TWITTER_USERNAME %}
<span class="linenos" data-linenos="23 "></span><meta name="twitter:site" content="@{{ TWITTER_USERNAME }}" />
<span class="linenos" data-linenos="24 "></span><meta name="twitter:creator" content="@{{ TWITTER_USERNAME }}" />
<span class="linenos" data-linenos="25 "></span>{% endif%}
<span class="linenos" data-linenos="26 "></span><meta name="twitter:image" content="INSERT-YOUR-TWITTER-IMAGE-LINK" />
<span class="linenos" data-linenos="27 "></span>{% if article and article.summary %}
<span class="linenos" data-linenos="28 "></span><meta name="twitter:card" content="{{ article.summary|striptags }}" />
<span class="linenos" data-linenos="29 "></span>{% else %}
<span class="linenos" data-linenos="30 "></span><meta name="twitter:card" content="{{ SITE_SUMMARY }}"/>
<span class="linenos" data-linenos="31 "></span>{% endif%}
</code></pre></div>
<h4 id="notes">Notes<a class="headerlink" href="#notes" title="Permanent link">¶</a></h4>
<ul>
<li>Grab your own Twitter’s avatar link do the following:</li>
<li>Go to your Twitter profile page</li>
<li>Right-click on your profile picture</li>
<li>
<p>Select “Copy image address” / “Copy image link”</p>
</li>
<li>
<p>For <code>OpenGraph</code> tags you may also consider to use <a href="https://github.com/whiskyechobravo/pelican-open_graph/tree/master">pelican-opengraph</a> plugin.</p>
</li>
<li>
<p>For all these to work properly, make sure <code>SITEURL</code>, <code>TAGLINE</code>, <code>SITE_SUMMARY</code>, <code>TWITTER_USERNAME</code> are properly defined in your <code>pelicanconf.py</code> alongwith in <code>publishconf.py</code> files. Please remember that definitions in <code>publishconf.py</code> only apply when you using <code>make publish</code> command.</p>
</li>
</ul>
<h3 id="loading-performance">Loading Performance<a class="headerlink" href="#loading-performance" title="Permanent link">¶</a></h3>
<h4 id="compress-everything">Compress everything<a class="headerlink" href="#compress-everything" title="Permanent link">¶</a></h4>
<ul>
<li>PageSpeed impacts <span class="caps">SEO</span> directly. Google punishes slow-site especially when search is made on a mobile device. Mobile-optimized sites will definitely rank higher on searches from mobile-devices.</li>
</ul>
<p>So, make sure all static files are compressed. If not, compress your themes theme’s <span class="caps">JS</span>, <span class="caps">CSS</span> files yourself to a <em>.min.</em> version and then replace those in the template files of the theme.</p>
<p>Or, better to use <a href="https://github.com/getpelican/pelican-plugins/tree/master/gzip_cache">gzip_cache</a> for gzipping all the <span class="caps">HTML</span> files statically, also and <a href="https://github.com/getpelican/pelican-plugins/tree/master/yuicompressor">yuicompressor</a> plugin for compressing <span class="caps">JS</span> <span class="amp">&</span> <span class="caps">CSS</span> files for Pelican. Those will make sure that, upon build, everything is compressed.</p>
<h4 id="utilize-cdn-if-you-can">Utilize <span class="caps">CDN</span> if you can<a class="headerlink" href="#utilize-cdn-if-you-can" title="Permanent link">¶</a></h4>
<ul>
<li>
<p>Use <span class="caps">CDN</span>-ed versions of common libraries(e.g. jQuery, Bootstrap etc.) rather than hosting your own copy, unless your theme actively modified it. Look it up on <a href="cdnjs.cloudflare.com">CloudFlare cdnjs</a>, <a href="https://cdnjs.com">cdnjs</a>, or on <a href="https://www.jsdelivr.com">jsdelivr</a> etc. and use those links.</p>
</li>
<li>
<p>Try to use a <span class="caps">CDN</span> for edge-distribution of your site. I only know of CloudFlare that provide this service for free for a single site. There might be others. <span class="caps">CF</span> also make managing <span class="caps">DNS</span> configuration little breezy.</p>
</li>
</ul>
<h3 id="engage-commenting">Engage commenting<a class="headerlink" href="#engage-commenting" title="Permanent link">¶</a></h3>
<p>While serving a static site, integrating a commenting-system looks a little far-fetched. However, blogs without proper commenting system feels kinda lame sometimes. Of course, <span class="caps">YMMV</span>.</p>
<p>But, it’s not difficult; easily can be done by systems like <a href="https://disqus.com/">Disqus</a> etc. I’m not affiliated with them, by the way.</p>
<h3 id="host-images-separately">Host images separately<a class="headerlink" href="#host-images-separately" title="Permanent link">¶</a></h3>
<p>Host all the images separately that you’ve used in your articles. Use image-specific hosting e.g. imgur.com, imgpile.com, UltraIMG.com, postimage.org etc.</p>
<p>But, why? Because, these services provide couple of benefits besides being free.</p>
<ul>
<li>Firstly, while loading the page, browser can parallelize loading from this hosts rather than your original blog hosts.</li>
<li>More often than not, these services use own <span class="caps">CDN</span>.</li>
<li>Often these services resize your uploaded images automatically to be used in different contexts, which enables you to choose the best-fit size on the fly but without doing it by hand.</li>
</ul>
<h2 id="other-tips">Other tips<a class="headerlink" href="#other-tips" title="Permanent link">¶</a></h2>
<h3 id="name-your-images-properly">Name your images properly<a class="headerlink" href="#name-your-images-properly" title="Permanent link">¶</a></h3>
<p>Because search-engines index images too. With proper names, images becomes relevant with the topic, hence potential to draw traffic.</p>
<h3 id="use-google-keyword-planner">Use Google Keyword planner<a class="headerlink" href="#use-google-keyword-planner" title="Permanent link">¶</a></h3>
<p>Even if you are not willing to blow money on ads, it will immensely help you to find out more searched for keywords.</p>
<h3 id="page-headers-controversial">Page-headers (controversial)<a class="headerlink" href="#page-headers-controversial" title="Permanent link">¶</a></h3>
<ul>
<li>Don’t use multiple 1<sup>st</sup>-level headers <code>H1</code> style. The main title link probably already have used it once. Look it up.
So, avoid it anymore, meaning avoid underlined-style(<code>=======</code>) or hash-style(single ‘#’) headers in your markdown files.</li>
</ul>
<p>However, 2<sup>nd</sup>-level <code>H2</code> tags can be (read ‘should be’) used multiple times. In case of markdown files, that’s <code>---------</code> underlines, or line starting with double-hash(‘##’).</p>
<h3 id="and-theres-lot-more">And, there’s lot more … ;)<a class="headerlink" href="#and-theres-lot-more" title="Permanent link">¶</a></h3>
<p>As I’ll gain more insights, I hope to grow this post. For now, this is a work-in-progress.<br>
Thanks for reading down so far. Adios !</p>R vs Python — A Summary Comparison2016-02-08T08:02:00+06:002016-02-08T08:02:00+06:00Khaled Monsoortag:blog.kmonsoor.com,2016-02-08:/R-vs-Python/<p>A tabular, objective, comparative summary view between R and Python programming languages. Facts matters.</p><table>
<thead>
<tr>
<th>..</th>
<th>R</th>
<th>Python</th>
</tr>
</thead>
<tbody>
<tr>
<td>Home</td>
<td><a href="http://r-project.org">http://r-project.org</a></td>
<td><a href="http://python.org">http://python.org</a></td>
</tr>
<tr>
<td><a href="http://githut.info/">Birth</a></td>
<td>1993</td>
<td>1991</td>
</tr>
<tr>
<td>Designer</td>
<td>Ross Ihaka, Robert Gentleman</td>
<td>Guido van Rossum</td>
</tr>
<tr>
<td>Package count</td>
<td>7,798 (<span class="caps">CRAN</span>)</td>
<td>73,402 (PyPI)</td>
</tr>
<tr>
<td>Purpose</td>
<td>statistical computing</td>
<td>General purpose</td>
</tr>
<tr>
<td>Paradigm</td>
<td>array, object-oriented, imperative, functional, procedural, reflective</td>
<td>object-oriented, imperative, functional, procedural, reflective</td>
</tr>
<tr>
<td>License</td>
<td><span class="caps">GPL</span></td>
<td><span class="caps">MIT</span></td>
</tr>
<tr>
<td>Platform</td>
<td>cross-platform</td>
<td>cross-platform</td>
</tr>
<tr>
<td>Implementations</td>
<td>Main, <a href="https://github.com/bedatadriven/renjin">Rejnin</a>, <a href="https://bitbucket.org/allr/fastr">FastR</a></td>
<td><a href="https://github.com/python/cpython">cPython</a>, <a href="https://bitbucket.org/pypy/pypy">PyPy</a>, <a href="http://www.jython.org">Jython</a>, <a href="https://github.com/IronLanguages/main/wiki">IronPython</a></td>
</tr>
<tr>
<td><a href="http://www.tiobe.com/index.php/content/paperinfo/tpci/index.html"><span class="caps">TIOBE</span><sup><span class="caps">TM</span></sup> index</a></td>
<td>19</td>
<td>5</td>
</tr>
<tr>
<td>Dev. <span class="caps">IDE</span></td>
<td>R Studio, Tinn-R, Architect</td>
<td>PyCharm, IPython/Jupyter, Spyder, Komodo <span class="caps">IDE</span></td>
</tr>
<tr>
<td>Graphics support</td>
<td>built-in, ggplot2, lattice, Vistat, googleVis</td>
<td>matplotlib, Seaborn, Plotly, Bokeh</td>
</tr>
<tr>
<td>Machine-learning</td>
<td>e1071, rpart, igraph, nnet, kernlab, caret</td>
<td>scikit-learn, PyML, PyMC, Shogun</td>
</tr>
<tr>
<td>Deep-Learning</td>
<td>H<sub>2</sub>O, Darch</td>
<td>TensorFlow, Theano, Decaf, <span class="caps">PDNN</span>, Keras, Caffe</td>
</tr>
<tr>
<td>Image-Analysis</td>
<td>Raster, EBImage, imager</td>
<td>scikit-image, OpenCV, scipy.ndimage</td>
</tr>
<tr>
<td><a href="http://githut.info/">Github project count</a></td>
<td>34,268</td>
<td>164,852</td>
</tr>
<tr>
<td>Latest release</td>
<td>2015-12-10 (Main: R-3.2.3)</td>
<td>2015-12-21 (cPython: Python 3.4.4)</td>
</tr>
</tbody>
</table>
<p><strong><span class="caps">N.B.</span></strong>
* Time-dependent data are up-to-date as of: <strong>2016-02-08</strong> * </p>
<p>…</p>Se7en Deadly Sins to Do in Python code2015-08-10T17:05:00+06:002015-11-21T00:05:00+06:00Khaled Monsoortag:blog.kmonsoor.com,2015-08-10:/seven-deadly-sins-in-python-code/<p>There are a lot of ways someone can make his (or her) Python code extremely difficult for himself and his fellow developers to work with and maintain. However, some are quite destructive by virtue. These ones are in my top-list.</p><h3 id="prelude">Prelude<a class="headerlink" href="#prelude" title="Permanent link">¶</a></h3>
<p>I have used the word “deadly” to express the potential to diminish the productivity of a Python programmer or his fellow teammate(s) who will work on the same code. Please take all these with quite a bit of salt, due to my limited expertise <span class="amp">&</span> limited experience with different types of projects based on Python.*</p>
<p><em>7</em> is just a catchy number. And, of course, this top list is subject to change along with my experience.<br>
You are also most welcome to suggest your own-finding to make into this list.</p>
<p>There are a lot of ways someone can make his (or her) Python code extremely difficult for himself and his fellow developers to work with and maintain. However, some are quite destructive by virtue. These ones are in my top-list.</p>
<h3 id="1-the-try-except-pass-trio"><strong>1. The <code>try: except: pass</code> trio</strong><a class="headerlink" href="#1-the-try-except-pass-trio" title="Permanent link">¶</a></h3>
<p>You know about design patterns, right ? At least, you know a little bit. </p>
<p>From <a href="https://en.wikipedia.org/wiki/Software_design_pattern">Wikipedia</a>,</p>
<blockquote>
<p>Design patterns can speed up the development process by providing tested, proven development paradigms.</p>
<p>Effective software design requires considering issues that may not become visible until later in the implementation. Reusing design patterns helps to prevent subtle issues that can cause major problems, and it also improves code readability for coders and architects who are familiar with the patterns.</p>
</blockquote>
<p>Now, think of the complete opposite of design-pattern. It is called <em>anti-pattern</em> which silently “destroys” efficiency in code. The below pattern can be considered the most deadly anti-pattern in Python code.<br>
<a href="http://redsymbol.net/">Aaron Maxwell</a> called it <a href="https://realpython.com/blog/python/the-most-diabolical-python-antipattern/">most diabolical</a> or “evil” anti-pattern.</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="k">try</span><span class="p">:</span>
<span class="linenos" data-linenos="2 "></span> <span class="n">subtle_buggy_operation</span><span class="p">()</span> <span class="c1"># possibly with I/O or DB operation</span>
<span class="linenos" data-linenos="3 "></span><span class="k">except</span><span class="p">:</span>
<span class="linenos" data-linenos="4 "></span> <span class="k">pass</span>
</code></pre></div>
<p>You thought to save some development time by “pass”ing them by. But, it will take hours, if not days, to find possible bugs, inside the block, later as all the exceptions are masked by the “pass” and the error location will be somewhere else outside this <code>try:except</code> block which may look like the most innocent code.</p>
<p>Again, quoting from Aaron …</p>
<blockquote>
<p>In my nearly ten years of experience writing applications in Python, both individually and as part of a team, this pattern has stood out as the single greatest drain on developer productivity and application reliability, especially over the long term.</p>
</blockquote>
<h3 id="2-wildcard-imports-ie-from-module-import">*<em>2. Wildcard imports i.e. <code>from module import *</code> *</em><a class="headerlink" href="#2-wildcard-imports-ie-from-module-import" title="Permanent link">¶</a></h3>
<p>This one single practice can render a nice (clean) module into a nightmare. According to a core Python developer <a href="http://python.net/~goodger/projects/pycon/2007/idiomatic/handout.html#importing">David Goodger</a>,</p>
<blockquote>
<p>Wild-card imports are from the dark side of Python.</p>
<p><strong>Never!</strong></p>
<p>The <code>from module import *</code> wild-card style leads to namespace pollution. You’ll get things in your local namespace that you didn’t expect to get. You may see imported names obscuring module-defined local names. You won’t be able to figure out where certain names come from. Although a convenient shortcut, this should not be in production code.</p>
<p><strong>Moral:</strong> don’t use wild-card imports!</p>
</blockquote>
<p>Also, in light of <a href="http://www.yodaquotes.net/">Yoda’s mythical conversation</a>s, David writes:</p>
<blockquote>
<p><span class="caps">LUKE</span>: Is from module import * better than explicit imports?<br>
<span class="caps">YODA</span>: No, not better. Quicker, easier, more seductive.<br>
<span class="caps">LUKE</span>: But how will I know why explicit imports are better than the wild-card form?<br>
<span class="caps">YODA</span>: Know you will when your code you try to read six months from now. </p>
</blockquote>
<p>If you use this practice in between inter-connected modules in a mid-sized project, worry not. You’ll start to get errors due to circular references soon enough.</p>
<p>Sounds funny ?</p>
<h3 id="3-thinking-that-tryexceptelse-construct-is-not-a-natural-control-flow-in-python"><strong>3. Thinking that <code>try:except:else</code> construct is not a natural control flow in Python</strong><a class="headerlink" href="#3-thinking-that-tryexceptelse-construct-is-not-a-natural-control-flow-in-python" title="Permanent link">¶</a></h3>
<p>If you are coming from Java(or, similar) world, I understand your confusion. However, Python adopted this construct so much different than Java. It helps to realize Python’s philosophy <a href="https://docs.python.org/2/glossary.html#term-eafp">Ask for Forgiveness than Permission</a>, aka “<span class="caps">EAFP</span> paradigm”.</p>
<p>Trying to avoid this will result in messy, unpythonic code. As this <a href="http://stackoverflow.com/a/16138864/617185">great answer on StackOverflow</a>, by a core Python developer, Raymond Hettinger, on this matter where he nicely portrays the philosophy behind it.</p>
<p>Quoting him :</p>
<blockquote>
<p>In the Python world, using exceptions for flow control is common and normal. Even the Python core developers use exceptions for flow-control and that style is heavily baked into the language (i.e. the iterator protocol uses <em>StopIteration</em> to signal loop termination). In addition, the try-except-style is used to prevent the race-conditions inherent in some of the “look-before-you-leap” constructs. </p>
<p>For example, testing <code>os.path.exists</code> results in information that may be out-of-date by the time you use it. Likewise, <code>Queue.full</code> returns information that may be stale. The <code>try:except:else</code> style will produce more reliable code in these cases. In some other languages, that rule reflects their cultural norms as reflected in their libraries. The “rule” is also based in-part on performance considerations for those languages.</p>
</blockquote>
<p>Also, consider checking out <a href="http://stackoverflow.com/a/180974/617185">this Q&A on StackOverflow</a> on the same premise.</p>
<h3 id="4-making-everything-a-class-aka-overusing-classes"><strong>4. Making everything a Class aka Overusing classes</strong><a class="headerlink" href="#4-making-everything-a-class-aka-overusing-classes" title="Permanent link">¶</a></h3>
<p>What I am referring to is <a href="https://www.youtube.com/watch?v=o9pEzgHorH0">this talk by Jack Diederich</a> on PyCon 2012. You should watch this couple of times and then once in every week.<br>
His summary is like … <strong>Stop</strong> creating classes, and modules in every now and then. Before creating one, think hard. Probably, what you need is writing just a function.</p>
<p><a href="https://www.python.org/dev/peps/pep-0020/">Zen of Python</a> described it as below.
Read it again, again, and again.</p>
<blockquote>
<ul>
<li>Beautiful is better than ugly.</li>
<li>Explicit is better than implicit.</li>
<li>Simple is better than complex.</li>
<li>Flat is better than nested.</li>
<li>Readability counts.</li>
<li>If the implementation is hard to explain, it’s a bad idea.</li>
</ul>
</blockquote>
<p>Though the below is a perfectly valid class, it is a perfect example case of b***sh*t classes:</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="k">class</span> <span class="nc">Greeting</span><span class="p">(</span><span class="nb">object</span><span class="p">):</span>
<span class="linenos" data-linenos="2 "></span> <span class="k">def</span> <span class="fm">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">greeting</span><span class="o">=</span><span class="s1">'hello'</span><span class="p">):</span>
<span class="linenos" data-linenos="3 "></span> <span class="bp">self</span><span class="o">.</span><span class="n">greeting</span> <span class="o">=</span> <span class="n">greeting</span>
<span class="linenos" data-linenos="4 "></span>
<span class="linenos" data-linenos="5 "></span> <span class="k">def</span> <span class="nf">greet</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">):</span>
<span class="linenos" data-linenos="6 "></span> <span class="k">return</span> <span class="s1">'</span><span class="si">%s</span><span class="s1">! </span><span class="si">%s</span><span class="s1">'</span> <span class="o">%</span> <span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">greeting</span><span class="p">,</span> <span class="n">name</span><span class="p">)</span>
<span class="linenos" data-linenos="7 "></span>
<span class="linenos" data-linenos="8 "></span><span class="n">greeting</span> <span class="o">=</span> <span class="n">Greeting</span><span class="p">(</span><span class="s1">'hola'</span><span class="p">)</span>
<span class="linenos" data-linenos="9 "></span><span class="nb">print</span><span class="p">(</span><span class="n">greeting</span><span class="o">.</span><span class="n">greet</span><span class="p">(</span><span class="s1">'bob'</span><span class="p">))</span>
</code></pre></div>
<p>It is doing exactly same as:</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="k">def</span> <span class="nf">greet</span><span class="p">(</span><span class="n">greeting</span><span class="p">,</span> <span class="n">target</span><span class="p">):</span>
<span class="linenos" data-linenos="2 "></span> <span class="k">return</span> <span class="s1">'</span><span class="si">%s</span><span class="s1">! </span><span class="si">%s</span><span class="s1">'</span> <span class="o">%</span> <span class="p">(</span><span class="n">greeting</span><span class="p">,</span> <span class="n">target</span><span class="p">)</span>
</code></pre></div>
<p>He also showed a practical example how he simplified (aka re-factored) an <span class="caps">API</span>’s complete code, consisting:</p>
<ul>
<li>1 Package, 22 Modules,</li>
<li>20 Classes,</li>
<li>660 Source Lines of Code</li>
</ul>
<p>into this below, a grand total of 8 lines. Yes, just 8 lines !!!</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="n">MUFFIN_API</span> <span class="o">=</span> <span class="n">url</span><span class="o">=</span><span class="s1">'https://api.wbsrvc.com/</span><span class="si">%s</span><span class="s1">/</span><span class="si">%s</span><span class="s1">/'</span>
<span class="linenos" data-linenos="2 "></span><span class="n">MUFFIN_API_KEY</span> <span class="o">=</span> <span class="s1">'SECRET-API-KEY'</span>
<span class="linenos" data-linenos="3 "></span>
<span class="linenos" data-linenos="4 "></span><span class="k">def</span> <span class="nf">request</span><span class="p">(</span><span class="n">noun</span><span class="p">,</span> <span class="n">verb</span><span class="p">,</span> <span class="o">**</span><span class="n">params</span><span class="p">):</span>
<span class="linenos" data-linenos="5 "></span> <span class="n">headers</span> <span class="o">=</span> <span class="p">{</span><span class="s1">'apikey'</span> <span class="p">:</span> <span class="n">MUFFIN_API_KEY</span><span class="p">}</span>
<span class="linenos" data-linenos="6 "></span> <span class="n">request</span> <span class="o">=</span> <span class="n">urllib2</span><span class="o">.</span><span class="n">Request</span><span class="p">(</span><span class="n">MUFFIN_API</span> <span class="o">%</span> <span class="p">(</span><span class="n">noun</span><span class="p">,</span> <span class="n">verb</span><span class="p">),</span> \
<span class="linenos" data-linenos="7 "></span> <span class="n">urllib</span><span class="o">.</span><span class="n">urlencode</span><span class="p">(</span><span class="n">params</span><span class="p">),</span> <span class="n">headers</span><span class="p">)</span>
<span class="linenos" data-linenos="8 "></span> <span class="k">return</span> <span class="n">json</span><span class="o">.</span><span class="n">loads</span><span class="p">(</span><span class="n">urllib2</span><span class="o">.</span><span class="n">urlopen</span><span class="p">(</span><span class="n">request</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">())</span>
</code></pre></div>
<p><strong>Moral:</strong></p>
<ul>
<li>Stop re-inventing the wheel,</li>
<li>use more of built-in library functions,</li>
<li>use much-less own long chains of class-hierarchy.</li>
</ul>
<p>Still want to see a worst scenario of creating classes? Check this out:</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="k">class</span> <span class="nc">Flow</span><span class="p">(</span><span class="nb">object</span><span class="p">):</span>
<span class="linenos" data-linenos="2 "></span> <span class="sd">"""Base class for all Flow objects."""</span>
<span class="linenos" data-linenos="3 "></span> <span class="k">pass</span>
<span class="linenos" data-linenos="4 "></span>
<span class="linenos" data-linenos="5 "></span><span class="k">class</span> <span class="nc">Storage</span><span class="p">(</span><span class="nb">object</span><span class="p">):</span>
<span class="linenos" data-linenos="6 "></span> <span class="k">def</span> <span class="nf">put</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">data</span><span class="p">):</span> <span class="n">_abstract</span><span class="p">()</span>
<span class="linenos" data-linenos="7 "></span> <span class="k">def</span> <span class="nf">get</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span> <span class="n">_abstract</span><span class="p">()</span>
<span class="linenos" data-linenos="8 "></span>
<span class="linenos" data-linenos="9 "></span><span class="k">def</span> <span class="nf">_abstract</span><span class="p">():</span> <span class="k">raise</span> <span class="ne">NotImplementedError</span>
</code></pre></div>
<p>Yes, this is a real piece of code from Google <span class="caps">API</span> client code. (which, in total, has <em>10,000 <span class="caps">SLOC</span>, 115 modules, 207 classes</em>). Whereas <a href="https://github.com/jackdied/python-foauth2">someone did implemented the same</a>, well maybe not extremely robust, but in <em>135 <span class="caps">SLOC</span>, 3 classes</em> in total.</p>
<p>You see the point, right? Guido did. <a href="https://plus.google.com/+JackDiederich/posts/iPiqWHjwcf3">Check his comment.</a></p>
<p><img alt="guido-google-comment" src="https://blog.kmonsoor.com/images/articles/guido-google-comment.jpg"></p>
<h3 id="5-saving-time-by-not-writing-any-documentation-or-inline-comments"><strong>5. Saving time by not writing any documentation or inline comments</strong><a class="headerlink" href="#5-saving-time-by-not-writing-any-documentation-or-inline-comments" title="Permanent link">¶</a></h3>
<p>If you don’t write comments with your semi-obfuscated code, and no docstrings as well saving time and meeting deadlines, stay assure that within a short period you’ll hate yourself when you will not remember what (& why) you did something while reading your own code.</p>
<p>Today or tomorrow, you will leave the company. And, that code will haunt all the members of your team who will come across this code-like zombies; unless they totally cut-off-the-head(e.g. replace) of your code.</p>
<p>There is just no excuse that you don’t do “documentation” except you just don’t care. If you would care, you would not only write minimal doc-strings and comments on complex code-sections, but also name your functions, methods, variables to reflect the purpose of the component to make them “self-documented”.</p>
<p>Here is a nice guide to properly <a href="http://docs.python-guide.org/en/latest/writing/documentation/">documenting your Python code.</a></p>
<p>However, there will still be deniers out there …</p>
<p><img alt="code-quality" src="http://i.imgur.com/Fzb8epA.png">
* source: <a href="https://xkcd.com/1513/">https://xkcd.com/1513/</a> *</p>
<h3 id="6-avoiding-unit-tests-and-doc-tests-until-the-doomsday-comes"><strong>6. Avoiding Unit-tests (and doc-tests) until the doomsday comes</strong><a class="headerlink" href="#6-avoiding-unit-tests-and-doc-tests-until-the-doomsday-comes" title="Permanent link">¶</a></h3>
<p>Yes, the judgement day will come.<br>
It will happen on the production server, with customer’s downtime due to a “completely” manually-tested new feature, which will break something “almost” unrelated.</p>
<p>Yes, your company can lose millions and <a href="http://dougseven.com/2014/04/17/knightmare-a-devops-cautionary-tale/">can be out of business.</a> Maybe after some sleep-less night of the development team, the “bug” would have found out.</p>
<p>Maybe, this whole mess could be simply avoided if the developer wrote his/her modules’ <a href="https://docs.python.org/2/library/unittest.html">unit-test</a> as well as <a href="https://docs.python.org/2/library/doctest.html">doctests</a> for the functions or methods. And, after implementing the feature he would have run the tests once across the project. The online book Dive-in-Python has an excellent introduction on <code>unittest</code>. Also, you can start with <a href="http://docs.python-guide.org/en/latest/writing/tests/#unittest">Hitchhiker’s guide’s introduction</a>.</p>
<h3 id="7-mixing-tab-and-space-in-the-same-file"><strong>7. Mixing <code>TAB</code> and <code>SPACE</code> in the same file</strong><a class="headerlink" href="#7-mixing-tab-and-space-in-the-same-file" title="Permanent link">¶</a></h3>
<p>You will need no more reason to curse yourself just a while after. It will haunt you whenever you’ll need to open the source-code in any editor other than your usual one. And, for others, “oh my! I can’t literally even…”.</p>
<p>While Python<strong>3</strong> will simply refuse to interpret this “half-breed” file, in Python<strong>2</strong>, the interpretation of <span class="caps">TAB</span> is as if it is converted to spaces using 8-space tab stops. So while executing, you may have no clue how a specific-line is being executed as part of which code-block.</p>
<p>For any code that you think someday someone else will read or use, to avoid confusion, you should stick with <a href="http://legacy.python.org/dev/peps/pep-0008/#tabs-or-spaces"><span class="caps">PEP</span>-8</a>, or your team-specific coding style. <span class="caps">PEP</span>-8 strongly discourage mixing <span class="caps">TAB</span> and Space in a same file.</p>
<p>Also, check out this <a href="http://programmers.stackexchange.com/a/197839/74557">Q&A on StackExchange.</a></p>
<blockquote>
<p>1. The first downside is that it quickly becomes a mess.</p>
<p>… Formatting should be the task of the <span class="caps">IDE</span>. Developers have already enough work to care about the size of tabs, how much spaces will an <span class="caps">IDE</span> insert, etc. The code should be formatted correctly, and displayed correctly on other configurations, without forcing developers to think about it. </p>
</blockquote>
<p>Also, <a href="http://www.secnetix.de/olli/Python/block_indentation.hawk">remember this</a></p>
<blockquote>
<p>Furthermore, it can be a good idea to avoid tabs altogether, because the semantics of tabs are not very well-defined in the computer world, and they can be displayed completely differently on different types of systems and editors. <br>
Also, tabs often get destroyed or wrongly converted during <em>copy-paste</em> operations, or when a piece of source code is inserted into a web page or other kind of markup code.</p>
</blockquote>
<h3 id="fin"><strong>Fin</strong><a class="headerlink" href="#fin" title="Permanent link">¶</a></h3>
<p>That’s all for now. That’s my list. This list hopes to evolve with my experience and expertise as well as the ever-changing collective wisdom of all the Python community.</p>
<p>What’s your take on the worst “un-pythonic” nightmares in Python code? Please feel free to share your 2-cents.</p>Python - How to Create All Possible Combinations (a.k.a Permutations)2014-01-31T00:00:00+06:002014-01-31T00:00:00+06:00Khaled Monsoortag:blog.kmonsoor.com,2014-01-31:/python-how-to-generate-all-possible-combinations-or-permutations/<p>Let’s say we have a string, or number. And, we want to generate all the combinations of all the characters of the string or the number</p><p>Let’s say the number is 123.</p>
<p>Then the statement:
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="s1">''</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">x</span><span class="p">))</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">permutations</span><span class="p">(</span><span class="nb">list</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="mi">123</span><span class="p">)))]</span>
</code></pre></div>
will create a sorted list of all possible numbers using ‘1’,‘2’ and ‘3’.
which is, [123, 132, 213, 231, 312, 321]</p>
<h3 id="what-it-is-doing">What it is doing<a class="headerlink" href="#what-it-is-doing" title="Permanent link">¶</a></h3>
<p>The part, <code>permutations(list(str('123'</code> is creating a <a href="https://en.wikipedia.org/wiki/Permutation">permutated</a> <a href="https://en.wikipedia.org/wiki/Tuple">tuples’</a> list of splitted string ‘123’.
And the <code>int(''.join(x))</code> is converting each tuple to Integer.</p>
<p>However, of course, you need to <code>import permutations from itertools</code>.</p>
<p>so, the generalized version would be:</p>
<div class="highlight"><pre><span></span><code><span class="linenos" data-linenos="1 "></span><span class="kn">from</span> <span class="nn">itertools</span> <span class="kn">import</span> <span class="n">permutations</span>
<span class="linenos" data-linenos="2 "></span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="s1">''</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">x</span><span class="p">))</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span><span class="p">(</span><span class="n">permutations</span><span class="p">(</span><span class="nb">list</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="p">))))]</span>
</code></pre></div>
<p>Python is fun. Isn’t it?</p>