抽象的なキーボードクラス

25130
記事: 4
登録日時: 8年前

抽象的なキーボードクラス

投稿記事 by 25130 » 8年前

プログラミングをする上で、
・抽象化は大事とか聞くけど、結局何に使うんだろう?
・理解したところで役に立つの?
という人は多数要ると思います。

この日記では「抽象化が必要」の具体例である、複数ライブラリ間のキーボードを実装してみたいと思います。
(似たような案件を掲示板で見かけた気がするので)

オブジェクト指向的発想としては、
「どの部分が変更されそうか」が重要になると考えています。
オフトピック
※1 C++の場合、コード量が増えそうなのでC#で書きます
※2 実在しないDxLibラッパーを使用しています
※3 実際には有用ではないクラスが出来上がりました
[hr]

次のコードは、とりあえずDxLibの環境でキーボードを実装してみた例です。

CODE:

public class Keyboard {
    public bool IsKeyDown(int keyCode) => DxLib.CheckHitKey(keyCode);
}
このクラスは、変化に対して柔軟でしょうか?
DxLibとしてのキーボードの役割を果たせそうですが、
.NET Frameworkとしてのキーボードの役割は果たせそうにありません。
(キーコードがintではなくSystem.Windows.Input.Keyであるため)

これら二つのキーボードの違いを見ると、キーコードの型を変更できれば実装できそうです。
そこで、次のようなインタフェースを設けてみます。

CODE:

public interface IKeyboard {
    bool IsKeyDown(TKeyCode keyCode);
}
オフトピック
しれっとジェネリクスの機能を使用していますが、近年の言語では大体似たような機能があるので問題ないと思います。
ジェネリクスの機能が無い場合、KeyCode自体を抽象化するかもしれません。
このインタフェースを利用すると、

CODE:

// DxLibとしてのキーボード
public class DxLibKeyboard : IKeyboard {
    public bool IsKeyDown(int keyCode) => DxLib.CheckHitKey(keyCode);
}

CODE:

using System.Windows.Input;

// .NET Framewrokとしてのキーボード
public class DotNetFrameworkKeyboard : IKeyboard {
    public bool IsKeyDown(Key keyCode) => Keyboard.IsKeyDown(keyCode);
}
「DxLibとしてのキーボード」「.Net Frameworkとしてのキーボード」の両方に対応する事が出来るようになりました。
めでたし。めでたし。

[hr]

正直のところ、キーボードを抽象化しても良い事は殆どありませんが、
「二つのライブラリのインタフェースが違うから実装できない」の解決策として、良い例となったのではないでしょうか。
最後に編集したユーザー 25130 on 2017年11月26日(日) 09:37 [ 編集 2 回目 ]

25130
記事: 4
登録日時: 8年前

Re: 抽象的なキーボードクラス

投稿記事 by 25130 » 8年前

直接は関係ないのですが、
IsKeyUp(T), IsKeyDownAny(T...), IsKeyDownAll(T...)みたいなのが追加されるのを見越して、
各具象KeyboardとIKeyboardの間にKeyboardを噛ませた方が良いかもしれませんね
(すべてIsKeyDown(T)の抽象メソッドを利用して実装できるので)
最後に編集したユーザー 25130 on 2017年11月26日(日) 11:34 [ 編集 1 回目 ]