久しぶりに

書いたら、インターフェースが大分変わってる。


MacBook Air 11インチ欲しい!


最近は汎用な感じにUNIX設定ファイルを書きなおしたり、
MUAmutt に変えたり、RSS Reader を newsbeuter に変えたり、
tmux を使ってみたり、端末大好きっ子です。


MacBook Air 11インチ欲しい!


特に newsbeuter は Google Reader みたいなキーボード移動好きな人にはオススメです。
個人的には、URL やタイトルをコマンドに渡したりできるので、後で web ページを丸ごと で取得したり、arxiv の気になる論文とかの pdf を取得したりするスクリプトを書いたりすると快適です。


MacBook Air 11インチ欲しい!


ちなみに最近 Mac OS X の端末ソフトは Google Code Archive - Long-term storage for Google Code Project Hosting. にした。
256色使えたり、UTF-8 ambigous character (例 ○ □)の全角表示とか対応していてなかなか素晴しいのです。


MacBook Air 11インチ欲しい!


というか、セミナーの準備とか、学会の準備とか、論文書く、とか、いろいろやらないと、いけないんですよ!!!!


MacBook Air 11インチ欲しい!


最後にこれだけはいっとく


MacBook Air 11インチ欲しい!

配列

d:id:konnyakmannan:20091212 をみて。
彼が FORTRAN の配列をどこで便利に感じているのかはわからないのだけれど、
C で任意次元配列をサブルーチンで扱うために一次元配列を利用するのを思いだした。
やり方は Row- and column-major order - Wikipedia
The N-dimensional array (ndarray) — NumPy v1.16 Manual
を見ればすぐわかる。
こんな指数を返す関数を作っておけばいい。C99 で書いてあるので注意。

// 総積の計算(多次元配列の全要素数を計算するのに使う)
int prod(const int* N, int rank){
    int prod = 1;
    for(int i=0; i<rank; ++i)
        prod *= N[i];
    return prod;
}
// 一次元配列の指数から多次元配列の指数を計算
void index_to_ndindex(int index, int* ndindex, int rank, const int* N){
    int base = index;
    for(int k=rank-1; k>=0; --k){
        ndindex[k] = base % N[k];
        base = (base - ndindex[k])/N[k];    
    }
}
// 多次元配列の指数から一次元配列の指数を計算
int index_from_ndindex(const int* ndindex, int rank, const int* N){
    int index = 0;
    int stride = 1;
    for(int k=rank-1; k>=0; --k){
        index += stride * ndindex[k];
        stride *= N[k];
    }
    return index;
}

例えば、三次元配列 A_{ijk} = ijk\quad i=0,\dots,4, j=0,\dots,5, k=0,\dots,2 を用意して、A_{431} を出力ってのを書くと。

int main(){
    const int rank = 3;
    const int N[] = {5, 6, 3};
    int size = prod(N, rank);
    double A[size];
    for(int i=0; i<size; ++i){
        int k[rank];
        index_to_ndindex(i, k, rank, N);
        A[i] = 1.0;
        for(int n=0; n<rank; ++n)
            A[i] *= k[n];
    }
    int k[] = {4, 3, 1};
    printf("%g\n", A[index_from_ndindex(k, rank, N)]);
}

FORTRAN で書いたルーチンを使うために column-major にするには、指数を返す関数内のループを逆に回せばいい。

めもりのせたけど、

起動したらECC えらーがでてる。
ECC えらーってそんなにでるもんなのかしら。
だとすると、Non-ECC ってこわい。

さて、メモリをいっぱいに使った計算でどのくらいかかるか知りたいけれど、
そのまえにいろいろなおさないといけない。

intel compiler

だと、jansson が一発 make できなかった。
icc

 $ CC=icc ./configure --prefix=$HOME
 $ make
 ...
 Making all in src
 /bin/sh ../libtool --tag=CC   --mode=compile icc -DHAVE_CONFIG_H -I. -I..    -Wall -Wextra -Werror -g -O2 -MT hashtable.lo -MD -MP -MF .deps/hashtable.Tpo -c -o hashtable.lo hashtable.c
 libtool: compile:  icc -DHAVE_CONFIG_H -I. -I.. -Wall -Wextra -Werror -g -O2 -MT hashtable.lo -MD -MP -MF .deps/hashtable.Tpo -c hashtable.c  -fno-common -DPIC -o .libs/hashtable.o
 icc: command line warning #10156: ignoring option '-W'; no argument required
 hashtable.c(66): error #177: variable "num_primes" was declared but never referenced
   static const unsigned int num_primes = sizeof(primes) / sizeof(unsigned int);
                            ^

 compilation aborted for hashtable.c (code 2)

icc が 宣言されてないけど一度も参照されてないよ。っていうことで
コンパイルオプションで -Werror がついていて、通常 warning ですむのがエラーになっているだけ。
ソースを読むほど時間は無いので*1

 $ sed -i.orig 's/-Werror//g' src/Makefile
 $ make
 $ make install

ですます。

*1:ほんとに正しいのは patch つけて報告しとくだよね。