C++的case声明?

问题描述:

我正在尝试将数字电子问题适应于基于C++ STL的程序。C++的case声明?

本来我有4个输入C1,C2,C3,C4。这意味着我有一个总的16种组合:

0000 
0001 
. 
. 
. 
1111 

我具有由

typedef std::pair<int, int> au_pair; //vertices 
typedef std::pair<int, int> acq_pair; //ch qlty 
typedef std::multimap<int, acq_pair> au_map; 
typedef au_map::iterator It_au; 

的没有限定的多重映射。的模拟取决于au_map的大小。 例如:如果au_map.size() = 5我会有C1,C2,C3,C4,C5。因此2^5 = 32例。

例如: 如果au_map.size()=4,我需要模拟我的算法16例。

for(It_au it = a_map.begin(); it != a_map.end(); it++) 
{ 
    acq_pair it1 = it->second; 
    //case 0: 
    //C3 = 0, C2 = 0, C1 = 0, C0 = 0 
    //Update it1.second with corresponding C values 

    //simulate algorithm 

    //case 1: 
    //C3 = 0, C2 = 0, C1 = 0, C0 = 1 
    //simulate 

    ......... 
    //case 15: 
    //C3 = 1, C2 = 1, C1 = 1, C0 = 1 
    //simulate 

} 

不是最好的主意。现在,您正在通过手动设置C1-C4并在for循环中编写一些仿真例程来做大量无用的工作。

将其自动化。

使用一些摘要State-Simulator映射器(其中Simulator实际上代表了一些具体的功能对象)。

typedef char State; 

struct basic_simulator { 
    // You could also pass some other parameters to your 
    // simulator 
    virtual void operator()(...) = 0 
}; 

struct concrete_simulator : public basic_simulator { 
    virtual void operator()(...) { 
     // Do something concrete 
     // Trolololo 
    } 
}; 

typedef basic_simulator Simulator; 

而且在这种情况下,您的实际包装看起来像std::map<State, Simulator*> map;


你需要做下一步要做的手段越来越C1-C4从它被定义为char你的状态值是什么。使用按位运算符。

您所有的状态都可以定义为0-15转换为二进制数字(2 -> 0010)。因此,要获得C1-C4值,你就只需要做出相应的转变:

// C1 C2 C3 C4 
// ----------- 
// 1 1 1 1 
State state = 15; 

for (int i = 3; i >= 0; i--) { 
    // State of some of the inputs, defined by one bit 
    InputState C_xx = ((state >> i) & 1); 
} 

现在只是所有这些0-15状态映射到适当的模拟仿函数:

std::map<State, Simulator*> mapper; 
// Generally speaking, you should use some sort of 
// smart pointer here 
mapper[0] = new concrete_simulator(...); 
mapper[1] = ... 

什么是真正的酷是例如,你可能只有3或4个具体的模拟器,这些模拟器会相应地映射到某些状态。

在这种情况下调用实际模拟将意味着类似:

// Fire appropriate simulation object 
    (*(mapper[actual_state]))(...); 

,并尽一切可能的仿真是指循环访问每个地图元素。


更新:同样的技术可用于其中必须超过输入状态/单输入状态可以具有多于可能的值。

只要写一个合适的映射函数和状态发生器即可。

+0

为什么std :: map更喜欢std :: vector?你肯定会获得更好的性能与std :: vector。 – andand 2010-06-24 15:41:07

+0

@andand在16个状态的情况下 - 是 - 'std :: vector'中的'O(N)'查找时间将比'std :: map'中的'O(log N)'查找时间好。但仅仅因为状态数量增长为'A^N',其中'A'代表可能的值,'N'代表输入数字,'std :: map'会给出更好的渐近性能。 **并且是 - 为什么在性能分析之前谈论性能?** – 2010-06-24 15:49:46

+0

@andand另外值得一提的是,'std :: map'可以很容易地切换到例如'boost :: unordered_map',赋予'O(1)'查找时间。 – 2010-06-24 15:51:06

哼......为什么不让for循环为你列举各种组合?

for (size_t i = 0; i != 16; ++i) 
{ 
    bool const c1 = i & 1; 
    bool const c2 = i & 2; 
    bool const c3 = i & 4; 
    bool const c4 = i & 8; 

    // your algorithm 
} 

比手工设置要容易一点。