2009年9月28日月曜日

[.NET]初Linq(LinqToSQL)

いまさら感がありますが、、、さっきはじめてLinqを使ってみました。えぇまぁLinq to SQLです。
Express Editionを使っているので、ちょっとメンドクサイ。

前準備は以下のとおり。
  1. ローカルデータベース(sdf)を作成する
  2. コマンドsqlmetal.exeで、LinqToSQLクラスを生成する("C:\program Files\Microsoft SDKs\Windows\v6.0A\bin\sqlmetal.exe" /dbml:Database1Context.dbml /context:Database1Context Database1.sdf)
コードはこんな感じ

private void button1_Click(object sender, EventArgs e)
{
    using (Database1Context context = new Database1Context("Database1.sdf"))
    {
        context.Log = Console.Out;
        var v = from test in context.T_TEST 
                 where test.PK_NO > 0
                 select test;
        foreach (var row in v)
        { 
            System.Diagnostics.Debug.WriteLine(string.Format("key:{0} data1:{1} data2:{2} date{3}", row.PK_NO, row.DATA1, row.DATA2, row.CDATE)); 
        }
    }
}

[SQL]JOIN=INNER JOIN

先日、とあるソースを見ていると、以下のようなSQLを見つけました。

SELECT * FROM tblTEST T1
JOIN tblTEST2 T2 ON T1.p_key=T2.p_key
WHERE ....


INNERでもLEFTでもRIGHTでもないJOINって?とおもって実行してみると、結局INNER JOINと等価でした。
・・・知りませんでした。

2009年9月25日金曜日

[SQL]n番目のレコード取得

SQLでソート後、n番目(この場合2番)を取得する方法を考えてみました。
コードはこんな感じ。


-- 分析関数で取得
SELECT * FROM (
SELECT *, Row_Number() OVER(ORDER BY p_key DESC) as RNK FROM tblTEST) T1
WHERE RNK=2

--ガッツで取得
SELECT top 1 * FROM tblTEST t1
WHERE t1.p_key<(SELECT MAX(p_key) FROM tblTEST)
ORDER BY p_key DESC


とりあえず、両方とも2番目が取れるものの、ガッツで取得のほうは、可読性も悪く、TotalSubtreeCostの結果もこのようになりました。

  • 集計関数→0.003934295
  • ガッツで取得→0.00657168

集計関数。。。覚えると便利そうですね。

2009年9月21日月曜日

[.NET]文字クラス

入力のチェックに、しばしば正規表現を使うことがあります。簡単なものからそうでないものまでいろいろあります。で、.NETでは、文字クラスというものが用意されております。なんでも「入力文字列と照合する文字のセット」だそうで。たとえば、いかのようなものがあります。
  • ひらがな→IsHiragana(3040-309F)
  • カタカナ→IsKatakana(30A0-30FF)
  • 漢字→IsCJKUnifiedIdeographs(4E00-9FFF)

で、たとえば、一文字以上の漢字であれば「^\p{IsCJKUnifiedIdeographs}+$」でいけるようです。こまかな話はよくわかりませんが、Unicode 4.0 および Perl 5.6 に基づいているようです。

2009年9月17日木曜日

[.NET]特殊なフォルダを取得する

先日.NETでSendToフォルダを取得する方法を調べていたのですが、意外と簡単に取れてしまいました。コードはこんな感じ。

Environment.GetFolderPath(Environment.SpecialFolder.SendTo);


えぇまぁたったコレだけなんです。
ほかにもは?とおもって検索してみると@ITにまとまった記事を発見しました。Windowsのシステム・フォルダのパスを取得するには?

備忘録代わりにメモ。

2009年9月13日日曜日

[.NET]ショートカット(lnk)を作成する(COM参照なし)

.NET Frameworkにはショートカット(lnkファイル)を作るインタフェースは提供されていません。
しかし、VBScriptではWScript.ShellのCreateShortcutを使えば簡単にショートカットを作ることができます。
そのため、.NETアプリケーションからショートカットを作りたければ、COM Interopすればよいことになります。具体的には「参照の追加」でCOM の「 Windows Script Host Object Model」を追加し、それらしいクラスを使ってVBScriptと同じような処理をすればよいことになります。しかし、アセンブリと同じフォルダにInterop アセンブリ(DLL)をおく必要があります。

個人的に・・・ですが、InteropのDLLをみるとげんなりしてしまいます。で、ほかの方法は無いか?と考えたときに、遅延バインディングでCOMを呼び出す方法を思い出しました。
VB.NETではコンパイルオプションで、遅延バインディングが可能ですが、あえてC#。コードはこんな感じ。

/// <summary>
/// ショートカットの作成
/// </summary>
/// <remarks>WSHを使用して、ショートカット(lnkファイル)を作成します。(遅延バインディング)</remarks>
/// <param name="path">出力先のファイル名(*.lnk)</param>
/// <param name="targetPath">対象のアセンブリ(*.exe)</param>
/// <param name="description">説明</param>
private void CreateShortCut(String pathString targetPathString description)
{
    //using System.Reflection;

    // WSHオブジェクトを作成し、CreateShortcutメソッドを実行する
    Type shellType = Type.GetTypeFromProgID("WScript.Shell");
    object shell = Activator.CreateInstance(shellType);
    object shortCut = shellType.InvokeMember("CreateShortcut"BindingFlags.InvokeMethodnullshellnew object[] { path });

    Type shortcutType = shell.GetType();
    // TargetPathプロパティをセットする
    shortcutType.InvokeMember("TargetPath"BindingFlags.SetPropertynullshortCutnew object[] { targetPath });
    // Descriptionプロパティをセットする
    shortcutType.InvokeMember("Description"BindingFlags.SetPropertynullshortCutnew object[] { description });
    // Saveメソッドを実行する
    shortcutType.InvokeMember("Save"BindingFlags.InvokeMethodnullshortCutnull);

}


コンパイラーにてシンタックス的なエラーを発見することができないのでアレですが、意外と簡単?ですね。

C# 4.0 では、言語レベルで遅延バインディング(Dynamic)がサポートされるようです。そうなるとこんな書き方はしなくてもすむんですけどね。

2009年9月8日火曜日

[他]VB.NETとC#のプロジェクトを混在させる(Express Edition)

#なぜ混在かアレですが。。。
いまかかわっている仕事では、C#/VB.NETと言語が混在するプロジェクトになっています。

それを解析・再構成する。ということでまだ調査段階のため、ツール類(製品版のVisual Studio)を導入することができない状態です。
で、ソース解析といってもエディタだけではしんどいので、とりあえず、C#/VB.NETのExpress Edhitionで開けるように調整しメソッドの呼び出し関係を簡単に開く(F12)することができるようになりました。
しかし、VB⇔C#の相互関係をF12で行き来することができないのでメンドクサイですが、そこは別々に調査していました。

ある日、VWDは両方の言語が使える環境であるため、もしかしたらソリューションに全部を統合できるかも。
と思ってやってみたらできちゃいました。
ほとんどが画面を持たないライブラリアプリケーションであったこともありますが、フリーでここまでの環境が作れるとは。。。いい時代になりました。

2009年9月4日金曜日

[他]Visual C#とVisual Web Developerのキーバインド

Visual C#では[F6]キーがビルドです、そのつもりでVWD(Visual Web Developer)で[F6]キーを押下すると無反応。VWDのビルドは[CTRL+B]なんです。
Visual C#でも[CTRL+B]でビルドできますが、指が[F6]になれちゃっているんです。

キーバインドは変更できるのですが、同じ系列のツールなのになんで違うんだろう?
ふしぎですねぇ。

2009年9月1日火曜日

[SQL]数値型フィールドで最小の空き番を取得する(その2)

先日紹介しましたGDD Blog: [SQL]数値型フィールドで最小の空き番を取得するでは、NOT INとNOT EXISTSを使ったSQLを紹介しました。あと、最近のDBMSではほとんど採用されている、集計関数を使った最小値を取得する方法があります。コードはこんな感じ。

SELECT
MAX(T1.ID) + 1 AS GAP
FROM (SELECT ID, Row_Number() OVER(order by ID) AS RNK FROM testtable) t1
WHERE ID = T1.RNK


実行効率については調べていません。がNOTを使っていませんので、他の方式よりよいと思われます。