2013-01-26

『すべての人に知っておいてほしい JavaScriptの基本原則』の執筆に参加しました


といってもコードが書けない人がターゲットなので、このブログを見るような方が買うと残念な事になります。私はAjaxの章とHTML5の章を担当しました。HTML5の章は途中でページが足りなくなってしまい、中途半端感がありますね。

このエントリーをはてなブックマークに追加

2013-01-14

Travis CIでブラウザ・Node.js両対応ライブラリをテストする

Struct.jsをnpmリポジトリに登録したついでにTravis CIでテスト実行するようにした。元々はブラウザ実行用のテストがjasmineを使って書いてあったが、ビルドサーバーでテスト実行できないので別の方式に変えた。

ブラウザ実行テスト

ヘッドレスブラウザのPhantomjsにjasmineのテストページのURLを食わせれば良い。Travis CIもPhantomjsが使える
phantomjs run-jasmine.js "http://localhost:9999/test/spec_runner.html"
がしかし、テストがことごとくfailしてどうにもならない。原因はPhantomjsがECMA Script6の機能をサポートしていない、オプションで有効にする事もできない故。とりあえずブラウザ実行テストは今回は諦める。

Node.js実行テスト

元々のテストコードをそのまま使いたかったのでjasmine-nodeを使って --harmony オプション付きでテスト起動する。各テストファイルの先頭に、Node.js対応のコードを追記しておく。
var Struct = (typeof(require) != 'undefined') ? 
    require(__dirname + '/../struct.js') : window.Struct;
npm testが動く様にpackages.jsonにコマンドを記述する。
packages.json
"scripts": {
  "test": "node --harmony ./node_modules/jasmine-node/bin/jasmine-node test"
},

Travis CI導入

githubと共にTravis CIを利用するのに必要な手順は次の二つ。

  1. Travis CIにgithubリポジトリのアクセス権を付与する
  2. .travis.ymlをリポジトリに追加してgithubにpushする。

npm testでテスト実行可能にしておけば、.travis.yml には特にテスト起動方法は書かなくて良い。
.travis.yml
language: node_js
node_js:
  - 0.8
branches:
  only:
      - master
npm testの前にnpm installも勝手にやってくれる。ステータスはTravis CIの画面で確認できて便利。
仕上げはおなじみの結果画像をReadmeに貼り付けて完了 →

このエントリーをはてなブックマークに追加

Struct.jsをnpmリポジトリに登録しました

Node.jsにも対応したので。npmリポジトリにも登録しました。v0.8.0以上、--harmony_proxiesオプション付きで起動すると動作します。

npm install struct-object



このエントリーをはてなブックマークに追加

2012-12-30

Box-Muller法と正規乱数生成器

PRML上巻の序章を読んだ頃に、ガウス分布に肄う乱数発生器を作りたいと思っていたので作ってみた。つまり、平均値と標準偏差を引数に取る乱数生成関数である。Web検索するとBox-Muller法を使うのと、中心極限定理を使う方法があるのでそれぞれ調べてみた。

Box-Muller法を使う

Box-Muller法は次の式によって作られる2つの独立変数を使うらしい。
$\sqrt{-2 * log(α)} * sin(2πβ)$
$\sqrt{-2 * log(α)} * cos(2πβ)$
式だけ見てもイメージが湧かないので、Octaveを使ってサンプル数2000でテストしてみた。
check_box_muller.matlab
clear;
alpha = rand(1, 1000);
beta = rand(1, 1000);
val1 = sqrt(-2 * log(alpha)) .* sin(2 * pi * beta);
val2 = sqrt(-2 * log(alpha)) .* cos(2 * pi * beta);
hist([val1,val2], 20);


ちゃんと正規分布っぽい。Box-Muller法で生成した標準正規分布に標準偏差を掛けて、平均値を足せば完成。
"use strict";

/**
 * @param {Number} mean 平均値
 * @param {Number} std 標準偏差
 */
function gaussianRandom(mean, std) {
  return randByBoxMullerTransform() * std + mean;
}

// Box Muller法を使って標準正規分布N(0,1)を得る
var randByBoxMullerTransform = (function() {
  var vals = [];

  function calc() {
    var alpha = Math.random(),
        beta = Math.random();
    return [
      Math.sqrt(-2 * Math.log(alpha)) * Math.sin(2 * Math.PI * beta),
      Math.sqrt(-2 * Math.log(alpha)) * Math.cos(2 * Math.PI * beta)
    ];
  }

  return function() {
    vals = vals.length == 0 ? calc() : vals;
    return vals.pop();
  }
})();

// Module export
module.exports = gaussianRandom;

中心極限定理を使う

中心極限定理を利用すると、複数の一様乱数の和を使うだけで標準正規分布N(0,1)が得られる。
"use strict";

/**
 * @param {Number} mean 平均
 * @param {Number} std 標準偏差
 */
function gaussianRandom(mean, std) {
  return randByCentralLimitTheorem() * std + mean;
}
 
// 中心極限定理を使って標準正規分布N(0,1)を得る
function randByCentralLimitTheorem() {
  var v = 0;
  for (var i = 0; i < 12; i++) {
    v += Math.random();
  }
  return v - 6;
}
 
// Module export
module.exports = gaussianRandom;
こっちの方が圧倒的に簡単でびびる。

このエントリーをはてなブックマークに追加

2012-12-27

autojumpをMacとUbuntuに導入した

サーバーとMacで共通のzsh用dotfilesを使っているのだが割とうまくいった。zshとautojumpの連携は、zshのプラグインマネージャのantigenを使った。

autojumpのインストール

Mac

brew install autojump

Ubuntu

sudo apt-get install autojump

dotfilesの設定

自分のdotfilesリポジトリにantigenをsubmoduleとして追加

cd dev/dotfiles
git submodule add https://github.com/zsh-users/antigen.git antigen
git submodule init
git submodule update

.zshrcからantigenを呼び出し

~/.zshrc
source ~/dev/dotfiles/antigen/antigen.zsh
antigen-lib
antigen-bundle autojump
antigen-apply

j がaliasとして使われるので、jのaliasを変更しておく。


このエントリーをはてなブックマークに追加