sphinx + breatheでAttributeError: 'NoneType' object has no attribute 'replace'

以下のようなエラーがSphinx + Breatheで出る。

# Sphinx version: 1.6.3
# Python version: 3.6.2rc1 (CPython)
# Docutils version: 0.13.1 release
# Jinja2 version: 2.9.6
# Last messages:
#   building [mo]: targets for 0 po files that are out of date
#
#   building [html]: targets for 1 source files that are out of date
#
#   updating environment:
#
#   1 added, 0 changed, 0 removed
#
#   reading sources... [100%] index
#
# Loaded extensions:
#   alabaster (0.7.10) from /usr/local/lib/python3.6/site-packages/alabaster/__init__.py
#   breathe (4.6.0) from /usr/local/lib/python3.6/site-packages/breathe/__init__.py
#   sphinx.ext.todo (1.6.3) from /usr/local/lib/python3.6/site-packages/sphinx/ext/todo.py
#   sphinx.ext.mathjax (1.6.3) from /usr/local/lib/python3.6/site-packages/sphinx/ext/mathjax.py
Traceback (most recent call last):
  File "/usr/local/lib/python3.6/site-packages/sphinx/cmdline.py", line 306, in main
    app.build(opts.force_all, filenames)
  File "/usr/local/lib/python3.6/site-packages/sphinx/application.py", line 339, in build
    self.builder.build_update()
  File "/usr/local/lib/python3.6/site-packages/sphinx/builders/__init__.py", line 331, in build_update
    'out of date' % len(to_build))
  File "/usr/local/lib/python3.6/site-packages/sphinx/builders/__init__.py", line 344, in build
    updated_docnames = set(self.env.update(self.config, self.srcdir, self.doctreedir))
  File "/usr/local/lib/python3.6/site-packages/sphinx/environment/__init__.py", line 583, in update
    self._read_serial(docnames, self.app)
  File "/usr/local/lib/python3.6/site-packages/sphinx/environment/__init__.py", line 602, in _read_serial
    self.read_doc(docname, app)
  File "/usr/local/lib/python3.6/site-packages/sphinx/environment/__init__.py", line 723, in read_doc
    pub.publish()
  File "/usr/local/lib/python3.6/site-packages/docutils/core.py", line 218, in publish
    self.apply_transforms()
  File "/usr/local/lib/python3.6/site-packages/docutils/core.py", line 199, in apply_transforms
    self.document.transformer.apply_transforms()
  File "/usr/local/lib/python3.6/site-packages/docutils/transforms/__init__.py", line 171, in apply_transforms
    transform.apply(**kwargs)
  File "/usr/local/lib/python3.6/site-packages/docutils/transforms/universal.py", line 294, in apply
    txtnode.parent.replace(txtnode, nodes.Text(newtext))
AttributeError: 'NoneType' object has no attribute 'replace'

breatheのbug

issueに解決方法が記載してある。 以下の該当行を次のコードで置き換えれば良い。

https://github.com/michaeljones/breathe/blob/d3eae7fac4d2ead062070fd149ec8bf839f74ed5/breathe/renderer/sphinxrenderer.py#L1103

        if nodelist:
            # nodelist[0].children = [term, separator] + nodelist[0].children
            nodelist[0].insert(0, term)
            nodelist[0].insert(1, separator)
        else:
            nodelist = [term]

numpyの演算

numpyの演算は、二次元の配列と一次元の配列を明確に区別している。 一次元の配列はvectorとして、二次元の配列はmatrixとして、数学的に許された演算のみ可能。 例えば、[0 1 2 3 4 5][[0 1 2 3 4 5]]の演算はできない。

def printVar(var, symboltable):
    for k, v in symboltable.items():
        if id(v) == id(var):
            print("{0}:".format(k))
            print(v)
            print("")

a = np.arange(6)
row_mat = np.arange(6).reshape(1, -1)
row_mat_trans = row_mat.T
col_mat = np.arange(6).reshape(-1, 1)
col_mat_trans = col_mat.T
add_mat = row_mat + col_mat_trans
mult_mat = row_mat.dot(col_mat)

printVar(a, locals())
printVar(row_mat, locals())
printVar(row_mat_trans, locals())
printVar(col_mat, locals())
printVar(col_mat_trans, locals())
printVar(add_mat, locals())
printVar(mult_mat, locals())

# operations causing errors
# mult_mat = a.dot(row_mat)

出力は

a:
[0 1 2 3 4 5]

row_mat:
[[0 1 2 3 4 5]]

row_mat_trans:
[[0]
 [1]
 [2]
 [3]
 [4]
 [5]]

col_mat:
[[0]
 [1]
 [2]
 [3]
 [4]
 [5]]

col_mat_trans:
[[0 1 2 3 4 5]]

add_mat:
[[ 0  2  4  6  8 10]]

mult_mat:
[[55]]

有限体の勉強するのに良い本

finite fields - Books on advanced galois theory - MathOverflow より引用。

Sierraのkarabiner elementsで日本語キーボードをUSキーボードっぽく使う

KarabinerはSierraにまだ対応していない。 Karabiner elementsでキーボードの配列を変更できるので、キーボードの配列を一文字ずついじってUSっぽく使うことはできる。

~/.config/karabiner/karabiner.jsonにキーの設定ファイルがあるので、以下を追記する。

Karabiner-Elements/README.md at master · tekezo/Karabiner-Elements

            "simple_modifications": {
              "0": "9",
              "1": "grave_accent_and_tilde",
              "2": "1",
              "3": "2",
              "4": "3",
              "5": "4",
              "6": "5",
              "7": "6",
              "8": "7",
              "9": "8",
              "caps_lock": "fn",
              "delete_forward": "equal_sign",
              "equal_sign": "hyphen",
              "hyphen": "0",
              "international1": "backslash",
              "international3": "equal_sign"
            },

次にKarabiner-Elementsを開きVirtual KeyboardのタブのKeyboard typeをANSIにしておく。

参考

std::stringでtolower/toupper

#include <algorithm>
#include <string> 

std::string data = "Abc"; 
std::transform(data.begin(), data.end(), data.begin(), ::tolower);
std::transform(data.begin(), data.end(), data.begin(), ::toupper);

Reference

MathJaxでQED記号をかく

MathJaxで証明終了の記号をかく。 記号自体は\Boxで与えられるが、右寄せにhtmlタグを使う必要がある。

<div class="QED" style="text-align: right">$\Box$</div>

class="QED"は特に意味がないので、消しても良い。

Travis CIでビルドの回数を抑える時

C++の場合は、一回のビルド・テストに非常に時間がかかるので、ビルドを減らしたい場合がある。 Travis CIでは、設定で

  • Build pushs
    • push時にビルド
  • Build pull requests
    • pull request 時にビルド

がある。 両方ONにすると、PR時に2回ビルドが走ることになる。 Travis CIの場合この2回のビルドは同じビルドではないが、PRのビルドだけ通れば十分である場合が多い。 以下のような設定を実現する方法を記載する。

  • PRでのbranchは全てビルド
  • pushでのビルドはmaster branchのみ

単純にBuild pushsをoffにすると、merge後のmasterのビルドが行われずに、badgeが更新されない。

補足

PRのビルドはmaster branchへのmerge後のビルドをしているので、pushのビルドとは異なる。 Travis CIが裏でmergeのコミットを作成し、ビルドしている。

方法

Travis CIの設定から以下をONにする。

  • Build pushs
  • Build pull requests

.travis.ymlに以下を記載する。

branches:
  only:
    # branchs through PR are built
    - master