「リンク可能なプロパティ」と呼ばれる、比較的タイプセーフ(ただし動的)で効率的なコンセプトを作成しようとしています。リンク可能なプロパティは、プロパティなどをバインドするC#の機能に似ており、シグナル/スロットモデルに似ています。
リンク可能なプロパティは、他のタイプの値にリンクできるタイプです。値が変更されると、すべての値が更新されます。これは、複数のプロパティ/値を同時に更新する必要がある場合に役立ちます。リンクを設定すると、すべてが自動的に処理されます。
- 任意のタイプから他のタイプにリンクできます(理論的には、これが問題です)
- リンクは、リストではなくリンクリストを使用します。これは、メモリと速度の両方でより効率的であり、このアプローチを使用することの本当の利点です。
- コンバーターは、値をあるタイプから別のタイプに変換するために使用されます(1から、必須、問題もあります)
- ゲッターとセッターのように振る舞うことができます。
私が苦労している問題は、リンクして任意のタイプに変換する機能を作成することです。次のコードは、小さな変更で機能します(テンプレート化されたChain関数をテンプレート化されていないバージョンに変換し、関数内でChange Chain<F>
toに変換します)。問題は、リンクが正しく呼び出されないことです。Chain
SetLink
このクラスはほぼ機能します(コンパイルと実行は行いますが、期待どおりには機能しません。上記の変更がないと、バインディング関数は呼び出されません。これはテストコードであり、適切にコード化されていません(静的カウンターの使用についてコメントしないでください。一時的な修正)チェーン要素とリンク要素は重要な側面です。
チェーンは、プロパティの値を変換して更新し、それを次のプロパティに渡す(または元の値の場合もある)と単純に想定しています。これは、元のプロパティに戻るまで続きます。元のプロパティに戻ると、プロパティは終了します。
#include <iostream>
#include <string>
#include <boost/bind.hpp>
#include <boost/function.hpp>
using namespace std;
static int iLCount = 1;
template <typename T>
class LinkableProperty
{
public:
std::string Name;
boost::function<void(T)> Link;
T Value;
template<typename F>
void Chain(F val)
{
Value = val;
std::cout << this->Name << " - " << this << ", " << &Link << ", " << val << " ! " << this->Value << " - " << "\n";
if (--iLCount < 0) return;
if (!Link.empty()) Link(Value);
}
LinkableProperty() { Link = NULL; Value = T(); Name = "Level " + std::to_string(iLCount++); };
void operator =(T value) { Value = value; }
template<typename F> void SetLink(LinkableProperty<F> &p)
{
Link = boost::bind(&LinkableProperty<F>::template Chain<F>, &p, _1);
}
void operator ()()
{
if (!Link.empty()) Link(Value);
}
};
int main()
{
LinkableProperty<unsigned short> L1;
LinkableProperty<double> L2;
L2.SetLink(L1);
L1.SetLink(L2);
L1 = 1;
L2 = 1.1;
L1();
cout << "----------\n" << L1.Value << ", " << L2.Value << endl;
getchar();
return 0;
}