更多原始内容被删除,以使问题更容易参考:
所以我有一个House班级有一个方法House.buy(Person p),导致这个人买房子.我想知道是否可以让人买房子,所以我也有一个方法House.tryBuy(Player p),如果人可以买房子.我有一个枚举BuyState与像值OK,NotEnoughMoney和AlreadyOwned.有几个不同的条件需要满足,客户想知道哪个失败了.但是如果多个条件失败怎么办?我可以有一个等级,比如House已经拥有而且Person没有足够的钱,返回BuyStates.AlreadyOwned.但这只能让我告诉客户一件事.
我可以有N个单独的条件和一个带有N*N值的枚举,ConditionA_AND_ConditionB_ANDConditionC但是由于几个原因这根本没有意义.我知道有些字段,每个条件都有一点,但它们看起来太低级,实现起来很烦人,而且不可扩展.所以我需要一种从枚举中返回值列表的方法,那么这样的类如何:
class C<type_of_enum> {
private List<type_of_enum> values;
//etc etc
}
Run Code Online (Sandbox Code Playgroud)
这是"最好的"设计吗?
(保持关于java和C#的问题以保持答案有效)
当我运行以下代码时,我正在观察奇怪的行为.我通过使用结构创建一个位域,我想使用52位,所以我使用long int.我的系统上long int的大小是64位,我在代码中检查它.不知怎的,当我尝试设置一位时,它设置了两位.其中一个是我想要设置的,第二个是第一个加上32的索引.任何人都可以告诉我,为什么?
#include <stdio.h>
typedef struct foo {
long int x:52;
long int:12;
};
int main(){
struct foo test;
int index=0;
printf("%ld\n",sizeof(test));
while(index<64){
if(test.x & (1<<index))
printf("%i\n",index);
index++;
}
test.x=1;
index=0;
while(index<64){
if(test.x & (1<<index))
printf("%i\n",index);
index++;
}
return 0;
}
Run Code Online (Sandbox Code Playgroud)
Sry忘了发布输出,所以我的问题基本上不可理解......它给出的输出如下:
8
0
32
这是合法的还是推荐的?我读到您应该只使用整数类型作为位字段,但这适用于布尔类型吗?这是可以的,还是这种不好的做法或未定义的行为?
struct MyStruct {
// ...
bool SomeBooleanProperty:1;
// ...
};
Run Code Online (Sandbox Code Playgroud) 考虑下面的结构,其中位域大小的总和是 64 位。为什么sizeof说这个结构是12个字节,什么时候应该是8个?
typedef struct wl_Ls {
unsigned int total:17;
unsigned int used:17;
unsigned int entrySize:17;
_Bool point:1;
} wl_Ls;
Run Code Online (Sandbox Code Playgroud)
[解决方案:] 对前 2 或 3 名成员使用 64 位类型修复程序修复它。解释在标记为解决方案的答案中
我有一个问题需要解决,但我不知道如何解决。我正在询问如何解决这个问题的一般想法。我有一个内存地址,在 ESI 中。内存代表某种简化的 ASCII 编码,其中 5 位依次表示一个特定字符。内存以五位结尾 - 00000b。为了转换为正常的 8 位 ASCII,必须将 60H 添加到每个 5 位值中。我想将每个 5 位编码字符存储为地址 EDI 下的 8 位 ASCII 编码。EDI 也必须以 0 - 00000000b 结尾。
示例: [ESI] = 00011 00010 11010 00000b [EDI] = 01100011 01100010 01111010 00000000b
我将如何从 esi 中逐个提取每 5 位?
我认为这应该可行,但我显然错了,但我不知道为什么:-) 假设我有来自网络 0x03 0x02 的以下字节。在我的脑海中,我希望它被转换为小端和以下联合
struct decoded {
uint16_t opcode : 12;
uint8_t unused : 1;
uint8_t numRegs : 3;
}
union words {
decoded a;
uint8_t byes[2];
}
Run Code Online (Sandbox Code Playgroud)
我希望我可以使用 be16toh(a.opcode) 并得到 0x030 并且 numRegisters 是 0x02。我发现,即使进行字节序转换,我也会得到 0x302 和 0x00 之类的结果,但我不知道为什么:-(
作为bitfields的新手,我需要一些建议,以了解我在网上看过的各种例子.我想使用位域而不是位掩码来提高可读性,以及稍后为新ppl维护.
这是声明位域的常用方法:
typedef enum
{
unsigned int x: 1;
unsigned int y: 1;
}statusBits1;
Run Code Online (Sandbox Code Playgroud)
到目前为止很好,然后我看到:
typedef enum
{
unsigned int x = 1 << 0,
unsigned int y = 1 << 1
}statusBits2;
Run Code Online (Sandbox Code Playgroud)
在我的学习中,我相信这会为任何statusBits2数据类型设置默认值.这是否也将x和y的大小设置为1比特字段,如statusBits1?两者的结合是我正在寻找的.
提前致谢.
编辑:谢谢你的答案!你强迫我重读我一直在学习的东西.我正在混合各种关于位域和位掩码的帖子的信息!
即:
在Objective-C中声明和检查/比较(bitmask-)枚举
http://forum.codecall.net/topic/56591-bit-fields-flags-tutorial-with-example/
我在C#/ C++工作几年后回到C,重新学习一点点.
因此,根据此处的C编译器标准:
http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1124.pdf
我们发现无法精确确定在C编译器中如何实现位字段的要求。显然,只要位域的行为与任何其他标量域一样,任何事情都会发生。文档部分6.7.2.1-10说:
“一个实现可以分配任何足够大的可寻址存储单元来容纳一个位域。如果有足够的空间,则紧跟在结构中另一个位域之后的位域应打包到同一单元的相邻位中。如果不足,保留空间,是否将不合适的位字段放入下一个单元或与相邻单元重叠是由实现定义的。一个单元内位字段的分配顺序(高位到低位或低位)到高级)是由实现定义的。可寻址存储单元的对齐方式未指定。”
对于许多声称“您不能信任位域”或“位域不可移植”的人来说,对编译器的迫在眉睫的自由似乎是一站式服务。该警报表明,整个编译器编写者和CPU制造商在星空中密谋,只是因为标准允许而笑着急于做一些奇特的位域调整和对齐。
这些疯狂的波西米亚风格的编译器/ CPU设计人员在哪里致力于保证位域永远不依赖和不便携,这些证据在哪里?我想看看火星上绿人的确凿证据。
我已经附上了简单易懂的C ++源代码,以告诉有关使用C ++编译器的任何系统的位域真相。我要问社区,不是征求意见,而是要向您的系统和编译器提供确切的输出证据,如果它们与发布的结果有所出入。如果与发布的结果相比,我有能力对整个C / C ++社区进行相同/不相同的投票,我想知道百分比是多少?
#include <stdio.h>
/*
A simple program to illustrate the bitfields actual internal compiled layout.
Results depend on machine architecture and compiler implementation and flags.
*/
typedef unsigned long long int ulli;
struct bitf
{
// field bits offset
ulli f0 : 1; // 0
ulli f1 : 2; // 1
ulli f3 : 3; // 3
ulli f7 : 4; // 6
ulli f15 : 5; // …Run Code Online (Sandbox Code Playgroud) 我试图创建一个具有32位总位数的位域结构,但是当我尝试为其分配32位数字时,出现此错误:
从'unsigned int'到位字段的隐式截断将值从4278190080更改为0
这是我的结构以及如何使用它
struct Color32 {
uint32_t a : 8;
uint32_t r : 8;
uint32_t g : 8;
uint32_t b : 8;
};
Color32 BLACK = {0xFF000000}; // this line has the compilation error
Run Code Online (Sandbox Code Playgroud)
我看到了有关位字段分配的其他问题,但它们似乎都使用按位运算来设置各个字段。
还有一个具有以下示例的参考,似乎与我使用它的方式相同,只有我自己不会编译:
#include <iostream>
struct S {
// three-bit unsigned field,
// allowed values are 0...7
unsigned int b : 3;
};
int main()
{
S s = {6};
++s.b; // store the value 7 in the bit field …Run Code Online (Sandbox Code Playgroud) 我NS_OPTIONS在 Objective-C 中给出了一个定义:
typedef NS_OPTIONS(NSInteger, MyType) {
MyTypeOption1 = 1 << 0,
MyTypeOption2 = 1 << 1,
MyTypeOption3 = 1 << 2,
// etc
}
Run Code Online (Sandbox Code Playgroud)
我正在将此类型导入 Swift,但无法形成位字段。
let default : MyType = MyTypeOption1 | MyTypeOption2
Run Code Online (Sandbox Code Playgroud)
错误:
Protocol 'BinaryInteger' requires that 'MyType' conform to 'BinaryInteger'
Run Code Online (Sandbox Code Playgroud)
IDE 表明问题出在常设冒号按位或运算符。
改变NS_OPTIONS声明或用 Swift 声明新类型OptionSet不是……选项。我怎样才能让 Swift 打球?
我在我们的一个组织数据文档中浏览,我遇到了以下代码.
struct A {
unsigned short int i:1;
unsigned short int j:1;
unsigned short int k:14;
};
int main(){
A aa;
int n = sizeof(aa);
cout << n;
}
Run Code Online (Sandbox Code Playgroud)
最初我认为大小将是6个字节,因为unsigned short int的大小是2个字节.但上面代码的输出是2个字节(On visual studio 2008).
有一点点的可能性i:1,j:1并k:14使它有点领域或什么?它只是一个猜测,我不是很确定.有人可以帮我吗?