SimpleBoxes

Re: Mac用テキストエディター選手権

ちょっとびっくりしてしまったので、一応補足しようと思います。

portal shit! さんの記事「Mac 用テキストエディター選手権」より。

まず単純に、いくつか「定番」と呼ばれているエディタ……例えば、Jedit X とか、BBEdit とか、TextWrangler とか、Smultron とか、TextMate とか、skEdit などがないなぁ、と思いました。あと私が常用している mi もありません。

miは使ったことあるけどあれもう一世代前のエディタじゃないですか?

はてなブックマーク - morygonzalezのブックマーク

何をもって「一世代前」と言っているのか分からないのですが、mi 自体は現在も精力的に開発が続いている現役アプリケーションだと私は認識しています。

以前 mi の簡単なチュートリアルを書いたこともあります。ちなみに mi はβ版を利用しています。まれに不安定なバージョンもあったりしますが、とりあえず現在の最新版 (2.1.9b5) は日常的に常用できるほど安定していると思います。

テキストエディタは道具なので、多くのユーザーの方は「世代がどう」と拘っていないと思っています。ただ、私もソフトウェアを開発しているので、その開発者という立場から見たときに「あれもう一世代前の」と言われるとちょっと悲しいかも……。

UIがイモいし

portal shit! : Mac用テキストエディター選手権

私自身は Dreamweaver にほとんど触れたことがないので分からないのですが、Dreamweaver は単体テキストエディタというよりも統合環境という印象を持っていて、Photoshop / Fireworks など他の Adobe アプリケーションとの連携が優れているんじゃないでしょうか。

ユーザーインタフェースが「イモい」の意味がよく分かりませんでした。古臭いという感じでしょうか。古くからあるツールは大幅にインタフェースを変えることは出来なかったりするので、ここら辺はジレンマを抱えているかもしれません。

確かに Coda は、素晴らしいテキストエディタです。

残念ながら、現状では個人的に「必須」と考えているいくつかの機能が欠けていて、mi の代わりになることはできませんけれども。

細かい部分での「見せ方」が凝っていて「おっ」と思わせるんですが (例えば、対応する括弧の表示方法など)、それが仰々しくなくて、ユーザービリティの向上につながっています。「使っていて心地よい」って感じさせる工夫が随所にあります。

ちなみに必須な機能のひとつが「矩形選択」です。Mac OS ではサポートしているエディタは少ないという印象があったのですが、調べてみたら、標準の「テキストエディタ」でもサポートされていました。

ちなみに私の調べた範囲では、

  • CotEditor
  • mi
  • Jedit X
  • TextMate
  • Xcode (のエディタ)
  • テキストエディト
  • vi / vim
  • emacs

で「矩形選択」がサポートされています。矩形選択は Coda の「ブロック編集」と相性がよいと思うので、是非ともサポートしてほしい機能のひとつです。

Terminalから直接呼び出して使う系のエディタ

portal shit! : Mac用テキストエディター選手権

いわゆる GUI なアプリケーションも Terminal 上から呼び出して使うことができます。

例えば、Coda を標準の「アプリケーション」フォルダにインストールしている場合、

open -a /Application/Coda.app 開きたいファイル

というコマンドで Coda を立ち上げることができます。

スポンサーリンク

Re: プログラマはそれを看過できない

ふうこさんに便乗。

今までどのくらいプログラミング言語を触ってきたか(3秒で挫折したものものも含む) - King of Programming Language - Open Object REXX blog for Japanese

the world loves the wannabees. | プログラマはそれを看過できない

今までどのぐらいプログラミング言語を触ってきたか。……日本語・英語は除きます。

明らかにプログラミング言語ではないものも含まれていますが、面倒なので、一緒くたにしています。

  • C++ (g++ / Visual C++)
  • C
  • Perl
  • JavaScript
  • HTML / XML
  • CSS
  • XSLT
  • cmd (DOS / コマンドプロンプト / Windows バッチファイル)
  • FORTRAN
  • Objective-C
  • アセンブリ言語 (DSP Ti/Lucent)
  • wiki 記法 (hatena / pukiwiki / などなど)
  • PHP
  • Python
  • Pascal
  • Hu-BASIC (ファミリーベーシック / X1)
  • bash / csh / zsh
  • SQL (MySQL / SQLite)
  • C#
  • Ruby
  • LaTeX
  • awk
  • sed
  • elisp
  • 秀丸マクロ
  • VBA
  • VHDL (ハードウェア記述言語)
  • tcl/tk
  • Java
  • AppleScript
  • HyperTalk
  • SmallTalk (Squeak)

ふうこさん同様、後ろの方は「触れただけ」という感じのものがずらり。

おそらくふうこさんが挙げ忘れたものもいくつかあるはずです。

マークアップ言語はプログラミング言語に入るかっていう弁当のバナナ的な疑問はあるものの。

the world loves the wannabees. | プログラマはそれを看過できない

やっぱり HTML / XML / wiki 記法などのマークアップ言語は、プログラミング言語ではない感じがします。

これ含めると、YAML とか JSON などのデータ記述言語はどうなんだ?正規表現も「言語」か? UML / DTD はどうなんだ?……とめどなく疑問が沸いてくるという印象です。

スポンサーリンク

Serene Bach セッション管理

Serene Bach では sb::Session というモジュールで、管理画面へのログインセッションを処理しています。

Serene Bach 3 での管理画面セッションの確認は、sb::App::Admin モジュールで行なっています。

Serene Bach におけるセッション処理のフロー自体はそれほど複雑ではありません。

[図] Serene Bach セッション処理フロー

コードに直すと以下のようになります。

  use sb::Session;
  
  # セッションオブジェクトの生成
  my $session = sb::Session->new('key' => 'session_key');
  
  if ( $session->check )
  { # セッションが有効
    my $extend = undef;
  
    # ... なんか処理を行なう ...
  
    if ( $extend )
    { # セッションを延長
      $session->start();
    }
    else
    { # セッションを終了
      $session->finish();
    }
  }
  else
  { # セッションが期限切れ、もしくは未発行
    my $login_success = undef;
  
    # ... パスワード確認処理 ...
  
    if ( $login_success )
    {
      $session->start();
    }
  }

sb::Session では、以下のメソッドを利用します。

check

有効なセッションが発行済かどうかをチェックします。

start

セッションを発行します。発行済の場合は再発行となり、セッション期限が延長されます。

finish

セッションを破棄します。このメソッドを実行しなくても期限切れのセッションは自動的に破棄されます。

セッションオブジェクトを生成する際に、渡している key がセッション整合に利用されます。

具体的には、この key を利用して cookie の発行などを行なっています。sb::Session モジュールは cookie の利用を前提に動作しているので、cookie が有効でない環境下では正しく動作しません。

関連記事

スポンサーリンク

Serene Bach テストコード

Serene Bach 3 の開発に当たり、ごく簡単なテストコードを作成して、公開前に簡易な動作チェックを行なっています。

lib/ ディレクトリ内にある test/ ディレクトリにテストコードがあります。

先ほど公開した Serene Bach 3.00 beta023 で有効なテストコードは

  • test_initparser.pl
  • test_loadall.pl
  • test_netaws.pl
  • test_netping.pl
  • test_plugins.pl

こられのテストコードをまとめて実行する「_testcases.pl」というスクリプトも用意されています。

これらのテストスクリプトは、lib/test/ をカレントディレクトリとして実行することを想定しています。

これらのテストコードは、テストを実行するためのモジュール sb::Test を使っています。

テストコードのメインルーチンは、非常にシンプルです。

  my $testcase = sb::Test->new();
  $testcase->add('plugins',\&_test,\&_check);
  $testcase->run();

add メソッドでテストケースを追加して、run メソッドで実行します。

add メソッドは、

  1. テスト名
  2. テスト用実行サブルーチン
  3. 期待値チェック

という引数を渡します。

テスト用実行サブルーチンは、関数をリファレンスを指定します。テスト用実行関数は何らかの出力を返して、その返り値を「期待値チェック」でチェックします。

期待値チェックは、期待する値そのものを指定するか、テスト用実行関数をチェックするためのサブルーチンのリファレンスを指定します。

サブルーチンのリファレンスが指定された場合、その期待値チェックサブルーチンには、テスト用実行関数の出力結果が引数として渡されます。

関連記事

スポンサーリンク

Serene Bach テンプレートの互換性問題

Serene Bach 2 のテンプレートでは、入れ子になった独自ブロックを擬似的に扱っています。

一方、Serene Bach 3 のテンプレートでは、入れ子になった独自ブロックをきちんと階層的に扱うように変更されました。

例えば、

_main-1
******
<!-- BEGIN test1 -->
test1-1
<!-- BEGIN test2 -->
test2
<!-- END test2 -->
test1-2
******
<!-- END test1 -->
_main-2

のような構成のテンプレートがあったとして、

  • 独自ブロック test1 を 2 回繰り返す
  • 独自ブロック test2 を 1 回繰り返す

という場合、

_main-1
******
test1-1
test2
test1-2
******
test1-1
test2
test1-2
******
_main-2

のようになるのが自然だと思いますが、Serene Bach 2 ではそのように出力することができませんでした。

Serene Bach 3 では、このような入れ子構成を維持したまま、テンプレート処理を行なうので、期待通りに出力されます。

しかしながら、その代償として「同じ名前の独自ブロックが離れて置かれた」ようなテンプレートに対して、Serene Bach 2 と同じように出力されないという互換性の問題がありました。

例えば、

_main-1
<!-- BEGIN test1 -->
<!-- BEGIN test3 -->
test3-1
<!-- END test3 -->
test1-1
test1-2
<!-- BEGIN test3 -->
test3-2
<!-- END test3 -->
<!-- END test1 -->
_main-2

のような構成のテンプレートがあった場合、独自ブロック test3 が離れた場所に二カ所あります。

これまでの Serene Bach 3 では、このようなテンプレートを Serene Bach 2 と同じように出力することができなかったので、テンプレートの修正が必要になっていました。

この互換性の問題は、Serene Bach 3 の次のβ版リリースで解消されます。これによりテンプレートに関して Serene Bach 2 との互換性がかなり向上しています。

スポンサーリンク

今日の進捗 2009.04.14

問題
与えられた配列の n 番目の要素 (先頭の要素は 0 番目とする) に対して、同じ値を持つ要素が、配列のその要素の前にいくつあるかを返す関数を作成して下さい。

例えば、以下のような配列

A,B,B,B,C,D,E,F,G,G,G,G,H,I,J,J,J,J,J,J,J,J,J,J,K,L

があった場合、

  • n = 0 の時は 0 (値が A である要素はひとつしかない)
  • n = 1 の時は 0 (値が B である最初の要素)
  • n = 2 の時は 1 (値が B である二番目の要素なので 1 を返す)
  • n = 3 の時は 2 (値が B である三番目の要素なので 2 を返す)
  • n = 4 の時は 0 (値が C である要素はひとつしかない)
  • ……以下、続く

のようになります。

とりあえずの解答 (perl のコード) は「続き」に。

続きを読む

スポンサーリンク

Serene Bach 多言語への対応

Serene Bach では、多言語対応を行なうライブラリとして sb::Language というモジュールが用意されています。

sb::Language の主な役割は二つ。

  • 定型文字列の多言語対応
  • 文字コードの変換

Serene Bach 3 になって仕組みは若干変わりましたが、基本的な内容はほぼ一緒です。

定型文字列の取得

例えば、

my $error = sb::Language->get->string('No article.');

のようにすると $error に「No article.」に対応した文字列がセットされます。

比較的よく利用されるインタフェースなので、Serene Bach 3 では

my $error = sb->string('No article.');

という形式のショートカットも用意されています。

言語リソースは特定ディレクトリ内にテキストファイルとして置かれています。

  • リソースディレクトリ (例 : /lib/resource/)
    • ja.txt : 日本語リソース
    • en.txt : 英語リソース

Serene Bach 2 では、基本的な言語リソースはモジュール内に記述されていましたが、Serene Bach 3 では上述のリソースファイルに移っています。

文字コード変換

文字コードの変換処理は sb::Language モジュールにあるインタフェースを利用します。

my $output = sb::Language->get->convert($input,'sjis');

現在のところ、あまり高度で複雑な処理などは想定されてなく、単に Jcode.pm のラッパーとして機能しています。

将来的には標準モジュールである Encode を利用するように変更したいところです。

Serene Bach のコンストラクタ

sb::Language は Singleton オブジェクトなので、どこで取得しても同一なオブジェクトが取得できることが保証されています。

Serene Bach では、new 以外に get がコンストラクタとして利用できます。

sb::Language->get->string('No article.');

のように、より自然な形で利用できるようにしています。

get コンストラクタは、sb::Object を継承した全てのクラスで利用できます。

関連記事

スポンサーリンク

mixi アプリを開発するのに携帯電話のメールアドレスが必須な件

「mixi アプリ」オープンβ版公開ということで、やはり一開発者としては気になるじゃないですか。

アプリ作成手順を見ると、まず開発者登録が必要らしいので、登録してみようと……

け、携帯電話のメールアドレスが必要なんですね、これ。……海外在住なので受け取れません。

そこで mixi 運営事務局にお問い合わせしてみました。頂いた返信メールにて

携帯電話をお持ちではない場合や、対応機種外の携帯をご利用の場合には、申し訳ございませんが、デベロッパー登録を行っていただくことはできかねます。

とのこと。

そう言えば、mixi に参加すること自体、携帯電話のメールアドレスが必須になったんでしたっけ。

携帯からの認証をおこなっていただかない限り、PCからの操作のみでは新規登録はできません。

(中略)

ユーザーの皆様にとってさらに安心感のあるコミュニティとしてmixi をご利用いただくために実施するもので、利用規約で禁止している迷惑行為等の被害を最小限にしていくための、安全性強化に関する取組みのひとつ

[mixi] ヘルプ > 登録 > 携帯がないと登録できないのですか?

ふむふむ。なるほど。

実際のところ、携帯電話のメールアドレスが必須になってから、当然ながら迷惑行為が減ったとして、どの程度の効果がこれまであったのか、一利用者としては気になるところです。

ちなみにインプレスが始めたサービス「GANREF」でもクラブメンバーになるのに mixi 同様「携帯電話のメールアドレスによる認証」が取り入れられています。

でも、mixi と決定的に違うのは、携帯電話がなくても登録する方法が用意されていることです (2009.04.11 現在)。

GANREF では、携帯電話がない場合、住所を記述して認証コードを郵送してもらうことで本人確認を行なっています。

[写真] GANREF から届いた認証メール

実際、私は海外から登録して、携帯電話のメールアドレスなしで GANREF のクラブメンバーになることができました。

ただし、私の場合認証コードの送付先は日本の住所を指定しました (海外の住所を受け付けているかどうかまでは確認していません)。

スポンサーリンク

コマンドプロンプト (cmd) 覚え書き

バッチファイル (.bat) は、定型作業を自動化するのに便利なので、それなりに利用します。

ディレクトリ内のファイルに対して個々にある操作を行ないたい

dir/b オプションを利用して、テンポラリファイルにファイル一覧を書き出し、for ループで回します。

例えば、develop ディレクトリ内のファイル・ディレクトリに対して svn cleanup / update を実行するバッチファイルは以下の通り。

dir /b develop > _tmp_file.txt
for /f %%L in (.\_tmp_file.txt) do  (
  svn cleanup develop/%%L
  svn update develop/%%L
)
del _tmp_file.txt

遅延環境変数の展開

コマンドプロンプトを利用する際、

cmd /v:on

を実行すると、「遅延環境変数の展開 (delayed environment variable expansion)」を有効にすることができます。

「遅延環境変数の展開」を有効にしておくと、バッチファイル内で環境変数をローカル変数のように扱うことができます。

環境変数をバッチファイル内に局所化するコマンドとして

setlocal

がありますが、その引数に enabledelayedexpansion を指定すると、バッチファイル内で「遅延環境変数の展開」を有効にすることができます。

なお、遅延評価された環境変数は以下のコードのように !VARIABLE! と「%」の代わりに「!」を使います。

setlocal enabledelayedexpansion
for /f %%L in (en ja fr) do  (
  set RSRC_DIR=resource\%%L\
  svn update !RSRC_DIR!
)
endlocal

バッチファイル内での入力受付

set/P オプションを利用すると、バッチファイルでユーザーに処理を尋ねるプロンプト表示を利用することができます。

例えば、引数が指定されていない場合にオプションを尋ねたい場合には

if "%1"=="" (
  set /P USERINPUT=option? 
  if not '%USERINPUT%'=='' set USERINPUT=%USERINPUT:~0,3%
) else (
  set USERINPUT=%1
)
if '%USERINPUT%'=='' goto usage

のようにします。

if not '%USERINPUT%'=='' set USERINPUT=%USERINPUT:~0,3%

がややトリッキーですが、これは入力された内容の最初の 4 文字だけを利用するためのおまじないです。

set/P オプションはファイルからのリダイレクトも利用できます。

例えば、file の内容を %FILEINPUT% にセットする場合、

set /P FILEINPUT<=file

のようなコードになります。

スポンサーリンク

Serene Bach 管理画面の構成

管理画面を処理する Admin アプリケーションは、Serene Bach 3 でも中核と言えるアプリケーションです。

その核となるモジュール sb::App::Admin は Serene Bach 3 のアプリケーションモジュール群の中で最も複雑な構造になっています。

[図] Admin アプリケーションの基本フロー

メニュー構築

メニュー構築は主に初期化処理にあたります。有効な管理用プラグインをロードして、メニューを構築する処理が含まれます。

ログイン処理

ログイン処理は基本的に sb::Session というセッション管理用モジュールを使って行なっています。

ページ処理

管理画面はそれぞれのメニューを「ページ」として処理するページドリブン的なアプローチを取っています。

基本的には各メニューごとにモジュールがあり、それぞれのモジュールがページ処理を行ないます。sb::App::Admin では、状況に合わせて適切なモジュールを起動します。

管理画面モジュールの基本コード

管理画面の各モジュールは、処理する内容・出力する内容について、ページ内容のみを考慮すればよい構成になっています。

そのため、プラグインも含め管理画面の個々のモジュールは、それほど複雑な構成にはなっていません。

sub callback
{
  my $self = shift;
  return ( $self->regi() )
    ? $self->_update(@_)
    : $self->_display(@_);
}
sub _update
{
  my $self = shift;
  my $msg = undef;
  # 
  # クライアント (ブラウザ) からの入力を処理する
  # 
  return $self->_display('message'=>$msg);
}
sub _display
{
  my $self = shift;
  my %param = (
    'message' => undef,
    @_
  );
  my $temp = sb::Template->new($self->load_template('file'=>TEMPLATE));
  # 
  # 出力内容を処理する
  # 
  $self->common_parts($temp);
  $self->set_message($temp,$param{'message'});
  return $self->set_main($temp->output);
}

ほとんどの管理画面モジュールは、上述のようなコードを踏襲しています。管理用プラグインも同様です。

関連記事

スポンサーリンク

5/13