Search on the blog

2014年1月29日水曜日

Spring Rooメモ

 Spring Rooの勉強メモ。

Spring Rooとは?
Enterprise Java開発のためのRADツール。
Roo ShellというCUIをインターフェースとしており、hintコマンドを使って対話的に開発ができる。

hintコマンドを打つとプロジェクトの状態を見て何をしたいか推測してくれて、次にやるべきことをsuggestしてくれる。suggestされたコマンドを入力すると、自動で設定ファイルやソースコード、テストコードを生成してくれる。

もちろん、Roo Shellを使わずにいつも使っているエディタからコードを書いてもいい。RooはRound-tripをサポートしているため、ソース変更を自動検知して影響のありそうなところをいい感じに変更してくれる。

Rooによって生成されたプロジェクトは、Spring, Hibernate, Tiles, AspectJ, Maveなどの標準的なJava技術によって構成される。しかも必要な機能を必要になったときにだけ自動的にインポートしてくれる。

Rooはビジネスロジックを書くことは出来ないが、インフラまわり、設定ファイルの管理を自動で行ってくれる便利なやつ。言い換えれば、開発者はビジネスロジックの実装に集中できるということ。

読んだドキュメント
分かりやすかったドキュメント類のまとめ。それぞれ何が書いてあるかメモしておく。

1.  Spring Roo公式ガイド Chapter 1 
Rooの概要、インストール方法、10分で出来るチュートリアルがある。

2.  Spring Roo公式ガイド Chapter 2
Rooコマンドによって何がなされる(何が生成される)かを説明している。
新たに以下の機能を説明。
  • 複数のEntity定義とEntity間のRelation定義の方法
  • Spring Securityを用いたアクセスコントロールの方法
  • IDEへのインポート方法
  • Look and Feelのカスタマイズ

ソースからビルドする方法が載っている。最新の機能を使いたかったり、Add-onを書きたかったりする場合に必要。
Tutorialは公式ガイド(Chapter 1, 2)のものと似たような感じなので特別やる必要はないと思う。


読んだソースコード
1. $ROO/samples/clinic.roo
基本的な機能が一通り実装されている。
  • トップレベルパッケージ配下の構成(web, domain, reference)
  • finder
  • 国際化機能


TODOs
  • data sourceの設定とかreverse engineeringからの開発とかについて説明したサイトをやる。
  • IBMのサイトの第二回目おもしろそうだからやる。
  • 公式リファレンスをChapter 6 までよむ。
  • $ROO/samples/配下のサンプルを動かしながらソース読むとよさそう。
課題
  • TutorialのSeleniumのテストが通らない。(同じ現象がForumにも上がっていたけど未解決)

2014年1月25日土曜日

サーバー奮闘記(26)特定のディレクトリ配下のみインデックス表示

特定のディレクトリ配下のみインデックス表示(ファイル一覧を表示)する場合の設定をメモ。

対象のディレクトリに.htaccessを作成して以下を記述。
Options +Indexes
IndexOptions SuppressLastModified SuppressSize
1行目でインデックスが表示される。2行目はオプションで最終更新日時、ファイルサイズの表示を抑制している。

あと、インデックスを表示すると表の下にサーバーのバージョンが表示されてしまう。
これはセキュリティ上好ましくないため、設定ファイルでServerTokensの値を変更する[1]。
Ubuntuの場合は、/etc/apache2/conf.d/securityで以下を設定する。
ServerTokens Prod
設定を変えたらサーバーを再起動。

References
[1] 10 Tips to Secure Your Apache Web Server on UNIX / Linux

2014年1月22日水曜日

大数の法則と中心極限定理をサイコロで確認してみる

 大数の法則(law of large numbers)と中心極限定理(central limit theorem)をサイコロで確認してみました。

大数の法則
大数の法則とは簡単に言うと以下のような法則です。

標本サイズを十分に大きくすると、標本平均は母平均に収束する。

ということで、サイコロ振りまくって標本サイズと標本平均の関係を下表にまとめてみました。
標本サイズ 標本平均
10 2.600
100 3.950
1,000 3.467
10,000 3.525
100,000 3.504
1,000,000 3.502
法則どおり、標本サイズを大きくしていくと母平均の3.5に収束していきました。

中心極限定理
中心極限定理は簡単にいうと以下のような定理です。

母集団の分布がどのようなものであっても、標本サイズを十分に大きくすると、母平均と標本平均の誤差は正規分布に従う。

簡単な例としてサイコロを2回ふって標本平均を算出する場合を考えます。
サイコロの目が(3, 4)だと標本平均は3.5になります。同様に(1, 6), (2, 5)の場合でも3.5になります。しかし(1,1)だと標本平均は1.0になります。
このように標本サイズが同じでも観測される事象によって標本平均は変化します。中心極限定理はこの確率的に変化する標本平均がどのような分布になるかについて言及しています。この定理のおもしろいところは「母集団の分布がどのようなものであっても」という枕詞の部分だと思います。

ということで、サイコロ振りまくって標本平均の分布をグラフにプロットしてみました。母集団の分布は離散一様分布であることに注意してください。

上からサンプル数=1, 3, 10です。



定理どおり正規分布の形になりました(※上のグラフにプロットしているのは標本平均の分布です。定理どおりに母平均との誤差をプロットしたグラフは3.5だけx軸負方向にシフトしたものになります)。
また、標本サイズを大きくすることで分散が小さくなっていることも確認できました。

2014年1月21日火曜日

Spring MVCの勉強

 会社でSpring MVCを使うことになりそうです。せっかくなので、家でも勉強していこうかなと思います。

以下勉強録&メモ書きです。

1日目: Hello World
まず、もっとも簡単なサンプルを動かしてみました。
以下のサイトが簡単でした。

Spring 3 MVC Hello World Example

ちょっとだけ詰まったところをメモ。
  • Eclipse上で動的WEBプロジェクトをMavenプロジェクトにするときは、まずDynamic Web Projectを新規作成して、そのあとConvert to Maven Projectする。
  • Tomcatのクラスパスにmaven dependenciesを加える方法はここを参照。
  • 上ページのとおりのURLでアクセスするためには、Tomcatに載せたModuleのPathは"/SpringMVC"とする。
Spring + Strutsの連携より設定がかなり簡単でした。ControllerがPOJOなのはシンプルでいいなと思いました。

2日目: Form Handling
フォームを使ったサンプルアプリケーションの実装をしました。

Spring MVC Form Handling Example

シンプルで分かりやすかったです。
@ModelAttributeを使っていますが、このサンプルでは無くても動きます。
@ModelAttributeの使い方は下(2つ目の箇条書き)にメモっておきます。
  • DispatchするJSP内で(Spring提供のtaglib)を使う場合は、model名を"command"にしなければならない。
  • @ModelAttributeアノテーションを使うとフォームモデルの名前を変更できる。アノテーションをつけないとデフォルトで型名から名前が付けられる。今回の例だとアノテーションをつけない場合、JSPから${student.id}のようにしてフォームモデルを参照できる。@ModelAttribute("hoge")を付与すると、${hoge.id}のようにしてアクセスできるようになる。
自動でいろいろやってくれるので便利な反面、何がどうなってその値が取得できるのかが分かり辛いです(慣れの問題だと思いますが)。

3日目: TilesとLogging
下のページをやってみました。

Tutorial: Spring 3 MVC Tiles Integration with Example in Eclipse. Tiles Spring Tutorial

Tilesは一貫したLook and Feelを保つためのテンプレートシステムらしいです。
header, menu, footerなどを部品化することが出来て便利です。
なんと、こんなのがあったのですか。手動でjspインクルードしてましたよ。

すぐ出来たので、サンプルのsystem.out.printのところをloggerで出すようにしてみました。
以下メモです。
  • Tilesを使ったビューの表示では、controllerが返すviewの名前とtiles.xmlのname属性が一致しているところに注目。ここでマッチングを行っている。
  • ログのfacadeはSLF4Jを使ってみた。src直下にlog4j.xmlを置けばそれだけでロガーが使えた。

2014年1月17日金曜日

C++ Iterator Invalidation

 以下のようなコードをサーバー上で実行すると、Runtime Errorになった。
ローカルだと正常に終了するけど何だろうなと思って調べていたらIterator Invalidationという現象が起こっていたことが分かった。
#include <set>
#include <iostream>

using namespace std;

int main() {
    int nums[] = {0,1,2,3,4,5,6,7,8,9};
    set<int> st(nums, nums+10);

    for (set<int>::iterator itr = st.begin(); itr != st.end(); itr++)
        if (*itr % 2)
            st.erase(itr);

    for (set<int>::iterator itr = st.begin(); itr != st.end(); itr++)
        cout << *itr << " ";

    cout << endl;
}
Iterator Invalidationとは、
Iterators are glorified pointers. Iterator invalidation is a lot like pointer invalidation; it means it suddenly points to junk data.
The problem occurs when a container that is being processed using an iterator has its shape changed during the process.
ということらしい[1]。

下のように書き直すと、Iterator Invalidationは起こらない[2]。itr++で現在のiteratorのコピーを返した後に、itrをインクリメントしているのがポイント。
#include <set>
#include <iostream>

using namespace std;

int main() {
    int nums[] = {0,1,2,3,4,5,6,7,8,9};
    set<int> st(nums, nums+10);

    for (set<int>::iterator itr = st.begin(); itr != st.end(); ) {
        if (*itr % 2)
            st.erase(itr++);
        else
            ++itr;
    }

    for (set<int>::iterator itr = st.begin(); itr != st.end(); itr++)
        cout << *itr << " ";

    cout << endl;
}
まー、実は上の例だと、remove_ifとerase使えば一発なんだけど。
実際サーバー上で走らせたコードはもう少し複雑で、フィルタリングに使う関数がシンプルな冪等関数じゃなかったので、functor使って簡単には書けなそうな感じだった。

他のSTLコンテナについても、Iterator Invalidationが起こる場合がある。どのような場合に気をつけないといけないかまとめてくれているサイトがあったのでリンクしておく。
References
[1] c++ - What is iterator invalidation? - Stack Overflow
[2] c++ - Deleting elements from STL set while iterating - Stack Overflow

2014年1月8日水曜日

2013年の振り返りと2014年の目標

 明けましておめでとうございます。恒例の去年の振り返りと今年の目標について書こうと思います。

去年の振り返り
去年立てた目標を一つずつ振り返っていこうと思います。

1.  週に4話英語の漫画を読む。
達成度 100%。
ワンピース、トリコ、黒バス、ナルトを毎週読みました。
あとナルトだけ最初から読んでないなと気づいて14年分くらい一気に読みました。暇人?というツッコミはなしでお願いします。

2. 「めぞん一刻」英語版アニメを全話見る。
達成度 100%。
夏くらいには全話見てしまっていました。英語版の響子さんも最高でしたね。
加えて英語の映画とかドラマとかを字幕なしで見るということにもチャレンジしました。喋り手が何をいいたいのかはだいたい分かるようになりました。
あとリスニングつながりで、聞き流しても洋楽の歌詞が頭に入ってくるようになりました。ある日突然いつもギタープレーが好きで聞いていた曲の歌詞がなぜか分かるようになったのです。「何これ?きもーい。」っていう変な感覚を覚えました。

3.  ESL PODのビハインド分をきちんとやる。
達成度 90%。
後半少し怠けてしまって、1ヶ月半分くらいのep.が未着手の状態で残ってしまいました。
今年は2013年と2014年のep.を攻略しようと思います。

4.  土日でその週に行われたCodeforcesの問題をすべて(div2のみ)解く。
達成度 79%。
この目標は少しやり方を変えて取り組みました。その週に行われたCodeforcesの問題を解くのではなく、過去問を解きました。理由は古い問題の場合Editorialが公開されており、ACされたソースが多数閲覧可能だったからです。
2013年にCodeforces Roundは63回開催されました。私が攻略した過去問のRound数は50でした。
また、去年チャレンジした問題は最終的にすべてアルゴリズムを理解した上で自力で実装できるようになりました。レッドコーダーの人たちもほとんど解けていないような問題も解説を読んだり、ACされたコードを読んだりして、最終的には解けるようになりました。

今年の目標
今年はちょっと気を抜いて遊びの時間も取り入れたいなと思います。
あとは最近読んだ田中ウルヴェ京さんの本が興味深かったので、メンタルトレーニングをやろうかと思います。
具体的に何をするかはもっと短期的な計画を考えるとして、年間の目標はざっとこんな感じです。
  1.  CodeforcesのRatingを1900にする。
  2. 土曜日は数学、英語、プログラミングをしない。
  3. メンタルトレーニング関連の書籍を読んで、実践してみる。
英語学習については、すでに生活の中に組み込まれているので敢えて目標には挙げませんでした。