Mac OS X (Lion) に python - scipy インストールする時の変更点

pip install scipy

としたところ、以下のエラーが出ました。

/usr/bin/cc -fno-strict-aliasing -O3 -w -pipe -DNDEBUG -g -fwrapv -O3 -Wall -Wstrict-prototypes -Iscipy/sparse/linalg/eigen/arpack/ARPACK/SRC -I/Users/akiraak/project/MRI-MFI/env/lib/python2.7/site-packages/numpy/core/include -c scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c -o build/temp.macosx-10.4-x86_64-2.7/scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.o
scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c:4: error: expected ‘;’, ‘,’ or ‘)’ before ‘float’
scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c:10: error: expected ‘;’, ‘,’ or ‘)’ before ‘float’
scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c:16: error: expected ‘;’, ‘,’ or ‘)’ before ‘*’ token
scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c:21: error: expected ‘;’, ‘,’ or ‘)’ before ‘*’ token

そこでソースコードに #include を追加してあげます。

  • scipy/sparse/linalg/eigen/arpack/ARPACK/FWRAPPERS/veclib_cabi_c.c
  • scipy/lib/blas/fblaswrap_veclib_c.c.src
  • scipy/linalg/src/fblaswrap_veclib_c.c

と、書いたけど上手くいっていないようなので試行錯誤してみる。

sqlite3 - Python 中央値を得る集計関数を追加する

sqlite には ORACLE のように中央値を取得する集計関数 MEDIAN が無いようです。しかし以下のように自前の関数を追加することができます。

import sqlite3

class Median:
    def __init__(self):
        self.values = []

    def step(self, value):
        self.values.append(value)

    def finalize(self):
        srtd = sorted(self.values)
        alen = len(srtd)
        return 0.5*(srtd[(alen-1)//2] + srtd[alen//2])

conn = sqlite3.connect("sqlite.db")
conn.create_aggregate("median", 1, Median)
cur = conn.cursor()
cur.execute("select median(data1) from table1")

sqlite3 - python DBファイルで:memory:を初期化する

sqlite3.connect(':memory:') でインメモリのDBを使う場合に中身を初期化しておきたい場合があります。一つの方法としてSQLを実行する方法があります。

conn = sqlite3.connect(':memory:', isolation_level=None)
c = conn.cursor()
sqls = [
    'CREATE TABLE table1 (data1 INTEGER, data2 INTEGER);',
    'INSERT INTO "table1" VALUES(1, 2);',
    'INSERT INTO "table1" VALUES(3, 4);'
]
for sql in sqls:
    c.execute(sql)


この方法でも良いのですが、データの量が多いと時間がかかります。たとえばカラム数4千でレコード数3万の場合2分ほど。これらの全てのカラムにインデックスを張った場合2時間ほどかかりました。


これでは時間がかかりすぎます。そこでSQLを実行するのではなく、事前に作成しておいたDBファイルをそのまま読み込んで初期化する方法を紹介します。


まずapswモジュールが必要になるので、こちらから落としてインストールしておきます。
そして、DBファイルで初期化を行う手順は以下のようになります。

import sqlite3
import apsw

_conn = apsw.Connection(':memory:') #1
conn = sqlite3.connect(_conn) #2
src_conn = apsw.Connection('src.db') #3

with _conn.backup("main", src_conn, "main") as backup:
    while not backup.done:
        backup.step(100) #4
  1. :memory: で apsw のコネクションを作成
  2. apsw で sqlite3 のコネクションを作成
  3. 初期化用のDBファイルで apsw のコネクションを作成
  4. 初期化用BDから :memory: へデータをコピーしていく

backup.step(100) で指定している数値は一度にコピーするページサイズです。小さくすればwhileが多く回りますが、適当な数値を入れておけば何を指定して問題ないと思います。


この方法を使うと、SQL文を実行したときにかかってた2時間が、なんと10秒まで短縮されました。

MHFのエラーを直す

モンスターハンター フロンティア オンライン シーズン2.0」がリリースされました。
しかし、ゲームを起動するとアップデートが始まって遊ぼうと思ったら、青画面に白文字!!エラー発生です。


何度ゲームを起動しなおしてもエラーの青画面が出ます。


でも、以下の手順で再インストールをする事で直りました。


1、「モンスターハンター フロンティア オンライン シーズン2.0」のアンインストール
  MHFにはアンインストーラーが無いので、コントロールパネルからアンインストールします


2、「C:\Program Files\CAPCOM\Monster Hunter Frontier Online」のフォルダを削除


3、「モンスターハンター フロンティア オンライン シーズン2.0」のインストール
  MHFのダウンロードはこちらから