« 2006年11月 | メイン | 2007年01月 »

2006年12月 アーカイブ

2006年12月02日

無料で使えるFirebird用の管理ツール

無料で使える Firebird 用の管理ツールを探してみました。

現在、検証中。

テーブルなどの操作にはFlameRobinを、データの閲覧にはIBConsole 日本語版+αを使うようにしました。

Firebird Wiki管理ツールの項目で他のツールも紹介されています。

2006年12月03日

図書館蔵書検索 searchlib 0.1.3

図書館蔵書検索 searchlib 0.1.3 を公開しました。

重複するISBNを削除する機能を追加しました。
右クリックで使用できます。

2006年12月04日

PythonでFirebirdを使う

PythonでFirebirdを使う。

インストール

  1. PythonのFirebirdライブラリ KInterbasDB をダウンロードする。
    Pythonはバージョン2.5、Firebirdは1.5.3なので、kinterbasdb-3.2.win32-FB-1.5-py2.5.exeをダウンロードしました。

  2. ダウンロードしたファイルを実行して、インストールする。

以上でインストールは完了。

Firebirdの接続と切断

import kinterbasdb
kinterbasdb.init(type_conv=200)
#データベースに接続する
con = kinterbasdb.connect(dsn='localhost:C:/path/to/file.FDB',
                          user='sysdba',
                          password='masterkey',
                          charset="SJIS_0208")
#切断する
con.close()

SELECT文

cur = con.cursor()
cur.execute("select * from ADDRESS")
for row in cur:
  print "postcode = %s, address = %s" % (row[0], row[1])

INSERT文

values = [('690-0001', '島根県松江市東朝日町'),
          ('690-0002', '島根県松江市大正町')]
cur = con.cursor()
cur.executemany("insert into ADDRESS values(?, ?)", values)
con.commit()

DELETE文

cur = con.cursor()
cur.execute("delete from ADDRESS")
con.commit()

2006年12月05日

Firebirdのbetween

Firebirdのbetween句は、範囲を指定する二つの値は昇順に記述しなくてはならない。

これは昇順に並んでいるので結果を取得できる。

select * from ADDRESS
where POSTCODE between 6900001 and 6900005

これは昇順ではないので結果が空になる。

select * from ADDRESS
where POSTCODE between 6900005 and 6900001

つまり、

between A and B

「AとBの間」ではなく、「A以上B以下」という意味だ。

2006年12月07日

日商簿記3級の報告

日商簿記3級に合格したので報告。

日商簿記3級の学習方法は、ひたすら問題を解くことだと思います。

テキストには『10日で合格(うか)る!日商簿記3級最速マスター』、問題集には『日商簿記3級テーマ別重要問題セレクト50』を使いました。

テキストには「10日で合格る…」とありますが、1日の分量が多いように思います。
1日何分の学習時間なのでしょうか。

問題集の方は要点が過不足なく押さえられていて、効率よく学習できるるように思います。

実際の試験では、他の受験生達の電卓を打つのがすごく早くて驚きました。音が全然違いました。「タタタタタ…」という感じ。こっちは「いち、ごー、さん…」という速度なのに。
電卓操作の練習をしておいても損はないと思いました。

調べてみると、『日商簿記受験生のための電卓操作完ぺき自習帳』という本がありますね。役に立つかも。

QuickReport Standard for BDS 2006

この QuickReport Standard ですが、Delphi for Win32 パーソナリティ用のみですが正式にダウンロードして頂けるようになりました。

QuickReport Standard

ということで、QuickReport Standard for BDS 2006のダウンロード先とインストールの詳しい手順が詳細されています。

C++Builderでも使えるのでしょうか?

今週は試す時間がとれそうにありません。

2006年12月12日

Borland Developer Studio 2006 / Turbo C++ 2006 から Boost を利用する

第3回デベロッパーキャンプのプレゼンテーション資料では、BCC32 5.8.x で Boost を利用する方法として基本的なコードを紹介しています。この記事では、さらに少し高度な利用例を解説します。

Borland Developer Studio 2006 / Turbo C++ 2006 から Boost を利用する

BDS2006からBoostを使う方法。

第3回デベロッパーキャンプのプレゼンテーション資料では、インストール方法が詳しく解説されています。
他にも、boost::regexなどのサンプルコードもありました。
ありがたいです。

2006年12月14日

QuickReport 4

この記事では、Borland Developer Studio 2006でQuickReport 4を使うためのインストール/環境設定の方法を解説します。また、既存のQuickReportアプリケーションをマイグレーションするときに、同時に考慮しておかなければならない注意点を説明します。

Borland Developer Studio 2006でQuickReport 4を使う

QuickReport 4 Professional(製品版)の入手方法、Delphi Win32・Delphi .NET・C++Builderへのインストール方法、など。

図書館蔵書検索 searchlib 0.1.4

図書館蔵書検索 searchlib 0.1.4を公開しました。

松江市立図書館の検索結果URLに貸し出し状況を表示するようにしました。

2006年12月15日

Delphi/C++Builder用データベースコンポーネント

Firebirdのメーリングリストで、Delphi用のデータベースコンポーネントが紹介されていました。
なかなか興味深いです。

Zeosがおもしろそう。ここにも記事がありました。MySQLやPostgreSQLにも対応しているみたい。

2006年12月16日

Python用IDE「PyDev」

Python用IDE「PyDev」の紹介。メモ。

島根県立図書館の資料検索ページが変更されている

島根県立図書館の資料検索ページが変わっていました。

松江市立図書館の資料検索ページと同じCGIプログラムを使っているようです。

以前の島根県立図書館の資料検索は検索結果が使い物にならず、検索結果から書名をコピーして、その書名で検索すると見つからないことがありました。

その点、松江市立図書館の資料検索は検索処理の方が、まともに動作します。

しかし、松江市立図書館の資料検索は使い勝手が悪い。
JavaScriptに問題があって、ブラウザの戻るボタンを押したときや、新しいウィンドウで開いたときに、正常に動作しません。

この問題が島根県立図書館の検索にも波及してしまいました。

図書館蔵書検索 searchlib 0.2.0

図書館蔵書検索 searchlib 0.2.0を公開しました。

  • 島根県立図書館の検索ページが変更されていたので、処理を変更しました。
  • 書名とAmazonへのリンクを追加しました

2006年12月17日

図書館蔵書検索 searchlib 0.2.1

図書館蔵書検索 searchlib 0.2.1を公開しました。

  • 出力するCSVファイルに書名とAmazonへのリンクを追加しました。
  • 書名の取得処理を修正しました。
  • Amazonへのリンクを修正しました。

2006年12月21日

JSEclipse

JavaScriptの開発の決定版!? AdobeからJSEclipse

AdobeのJSEclipse

  • シンタックスハイライト
  • 補完機能
  • 定義部分へのジャンプ機能
  • JavaScriptマニュアルとの連系機能
  • キーワードハイライト機能

など一通りの機能はそろっているらしい。

2006年12月29日

C++BuilderによるUnlha32.dllを使用した書庫の展開(1)

C#で書かれた「Unlha32.dll」を使用した書庫の展開を参考にしながら、 C++Builderで書庫を展開するコードを作成しました。

main() 関数

C#ではデスクトップの絶対パスを取得するのに System.Environment.GetFolderPath() を使用しています。
C++Builderでは、同様の機能がライブラリにないため、Win32API を使って実装しました。(GetFolderPath()関数)

C#では、パスから拡張子部分をのぞいたファイル名を取得するのに Path.GetFileNameWithoutExtension() を使用しています。
C++Builderでは、ChangeFileExt() を使い、同様の機能を実現しました。

GetFolderPath() 関数

GetFolderPath()関数は、デスクトップの絶対パスを取得する関数です。
SHGetMalloc()などを使用するために、#include vcl.h の前に、shlobj.h を include します。

#define NO_WIN32_LEAN_AND_MEAN
#include <shlobj.h>
#include <vcl.h>

LhaExtractArchive()関数

UNLHA32.DLLで書庫を展開する関数です。

C#の System.IO.File.Exists() と同様の機能が、C++Builder では FileExists() になります。

C#のプログラムでは SearchPath() で、DLLの有無を確認しています。
C++Builderの方は、実際にDLLをロードしてその成否によって確認するようにしました。
VCLのクラスである TDll を使うと、デストラクタで FreeLibrary() が呼ばれるため、自分で記述する必要が無くなり、ソースコードが簡潔になります。
TDllを使うには、utilcls.h を include します。

//DLL(Unlha32.dll)の読みこみ
TDll dll("unlha32.dll");
  //DLLの存在を確認
  if (!dll)
  {
    throw Exception("UNLHA32.DLLが見つかりません。");
  }

C#では、DLLの関数を使用するのに DllImport を使用します。
C++Builderでは、GetProcAddress() で関数のアドレスを取得して使用します。

typedef WORD (WINAPI *PUnlhaGetVersion)(void);
PUnlhaGetVersion UnlhaGetVersion = (PUnlhaGetVersion)dll.GetProcAddress("UnlhaGetVersion");
WORD ver = UnlhaGetVersion();

ToCommandStringFromFile()

ファイル名をコマンドとして適切な文字列に変換する関数です。
ホームページ上にはありませんが、ダウンロードしたソースコードには、この関数が作成されていました。

C#では、StartsWith() や EndsWith() が便利ですね。
C++Builderでは、AnsiPos() や SubString() を使いました。
もっと上手な方法がありそうです。

一方、文字列をダブルクオート(")でくくる処理が、C#では、

cmd = "\"" + cmd + "\"";

となっているところを、C++Builderでは、AnsiQuotedStr() を使い、

cmd = AnsiQuotedStr(cmd, '"');

と書けます。

ソースコード

//---------------------------------------------------------------------------

#define NO_WIN32_LEAN_AND_MEAN
#include <shlobj.h>
#include <vcl.h>
#pragma hdrstop
#include <stdio.h>
#include <utilcls.h>
#include <string.h>
//---------------------------------------------------------------------------

#pragma argsused
//---------------------------------------------------------------------------
/**
 * デスクトップのファイルを物理的に格納するフォルダのパスを取得する
 * @return フォルダのパス。エラーが発生した時は、""
 */
AnsiString GetFolderPath()
{
  PItemIDList PIDL;
  LPMALLOC malloc;

  // IMallocインターフェイスへのポインタを取得
  SHGetMalloc(&malloc);

  //フォルダの識別子を取得
  if (FAILED(SHGetSpecialFolderLocation(Application->Handle, CSIDL_DESKTOPDIRECTORY, &PIDL)) == TRUE)
  {
    return "";
  }

  // 識別子をディレクトリに変換
  char szPath[MAX_PATH + 1];
  SHGetPathFromIDList(PIDL, szPath);
  malloc->Free(PIDL);

  return AnsiString(szPath);
}
//---------------------------------------------------------------------------
/**
 * ファイル名をコマンドとして適切な文字列に変換する
 * @param fileName ファイル名
 * @return コマンドとなる文字列
 */
AnsiString ToCommandStringFromFile(AnsiString fileName)
{
  AnsiString cmd = fileName;

  //ファイル名が「-」や「@」ではじまる時は、「.\」を付加
  if (cmd.AnsiPos("-") == 1 || cmd.AnsiPos("@") == 1)
  {
    cmd = ".\\" + cmd;
  }

  //ファイル名にスペースが含まれる時は、"で囲む
  if (cmd.AnsiPos(" ") != 0 &&
      !(cmd.AnsiPos("\"") == 0 && cmd.SubString(cmd.Length(), 1) == "\""))
  {
    cmd = AnsiQuotedStr(cmd, '"');
  }
  return cmd;
}
//---------------------------------------------------------------------------
/**
 * UNLHA32.DLLで書庫を展開する
 * @param archiveFile 書庫ファイル名
 * @param extractTo 展開先のフォルダ名
 */
void LhaExtractArchive(AnsiString archiveFile, AnsiString extractTo)
{
  //指定されたファイルがあるか調べる
  if (!FileExists(archiveFile))
  {
    throw Exception("指定されたファイル'" + archiveFile + "'が存在しません。");
  }

  //DLL(Unlha32.dll)の読みこみ
  TDll dll("unlha32.dll");

  //DLLの存在を確認
  if (!dll)
  {
    throw Exception("UNLHA32.DLLが見つかりません。");
  }

  //DLLのチェック
  typedef WORD (WINAPI *PUnlhaGetVersion)(void);
  PUnlhaGetVersion UnlhaGetVersion = (PUnlhaGetVersion)dll.GetProcAddress("UnlhaGetVersion");
  WORD ver = UnlhaGetVersion();
  printf("UNLHA32.DLLのバージョン:%d\n", ver);

  //動作中かチェック
  typedef BOOL (WINAPI *PUnlhaGetRunning)(void);
  PUnlhaGetRunning UnlhaGetRunning = (PUnlhaGetRunning)dll.GetProcAddress("UnlhaGetRunning");
  if (UnlhaGetRunning())
  {
    throw Exception("UNLHA32.DLLが現在動作中です。");
  }

  //展開できるかチェック
  typedef BOOL (WINAPI* PUnlhaCheckArchive)(LPCSTR, const int);
  PUnlhaCheckArchive UnlhaCheckArchive = (PUnlhaCheckArchive)dll.GetProcAddress("UnlhaCheckArchive");
  if (!UnlhaCheckArchive(archiveFile.c_str(), 0))
  {
    throw Exception("UNLHA32.DLLでは展開できません。");
  }

  //展開先フォルダの作成
  bool createdDir = false;
  if (!DirectoryExists(extractTo))
  {
    ForceDirectories(extractTo);
    createdDir = true;
  }

  //ファイル名とフォルダ名を修正する
  archiveFile = ToCommandStringFromFile(archiveFile);

  //フォルダ名は必ず\で終わる必要がある
  extractTo = IncludeTrailingPathDelimiter(extractTo);
  extractTo = ToCommandStringFromFile(extractTo);

  //展開する
  typedef int WINAPI (*PUnlha)(const HWND, LPCSTR, LPSTR , const DWORD);
  PUnlha Unlha = (PUnlha)dll.GetProcAddress("Unlha");
  char output[1024];
  AnsiString cmdLine = AnsiString().sprintf("x %s %s *", archiveFile, extractTo);
  int ret = Unlha(Application->Handle,
                  cmdLine.c_str(),
                  output, sizeof(output));
  //結果
  if (ret != 0)
  {
    //展開先フォルダが空の時は削除(削除できないかも)
    if (createdDir)
    {
      RemoveDir(extractTo);
    }

    throw new Exception("書庫の展開に失敗しました。");
  }
  printf(output);
}
//---------------------------------------------------------------------------
int main(int argc, char* argv[])
{
  if (argc < 1)
  {
    printf("展開するファイルが指定されていません。");
    return 0;
  }

  //展開
  for (int i = 1; i < argc; ++i)
  {
    AnsiString f = argv[i];
    //展開先を決定
    AnsiString extractDir = GetFolderPath();
    extractDir = IncludeTrailingPathDelimiter(extractDir) +
                 ChangeFileExt(ExtractFileName(f), "");
    //展開
    try
    {
      LhaExtractArchive(f, extractDir);
      printf("%sを%sに展開しました。\n", f.c_str(), extractDir.c_str());
    }
    catch (Exception &E)
    {
      printf("%sの展開に失敗しました。\n", f.c_str());
      printf("ERROR:%s\n", E.Message.c_str());
    }
  }

  getc(stdin);
  return 0;
}
//---------------------------------------------------------------------------

2006年12月31日

FirebirdでDDLを抽出する方法

Firebirdでは、isql の -x オプションで DDL が抽出できます。

-x 指定されたデータベースに対して DDL を抽出します

コマンドラインツールの簡易マニュアル

isql -x データベース名 -u ユーザ名 -p パスワード

About 2006年12月

2006年12月にブログ「山本隆の開発日誌」に投稿されたすべてのエントリーです。過去のものから新しいものへ順番に並んでいます。

前のアーカイブは2006年11月です。

次のアーカイブは2007年01月です。

他にも多くのエントリーがあります。メインページアーカイブページも見てください。

Powered by
Movable Type 3.35