我有大量的C结构实例,如下所示:
struct mystruct
{
/* ... */
unsigned flag: 1;
/* ... */
};
Run Code Online (Sandbox Code Playgroud)
flag 最初为0但在退出某个函数时必须为1.最简单的实现是:
void set_flag(struct mystruct *sp)
{
sp->flag = 1U;
}
Run Code Online (Sandbox Code Playgroud)
但是这样做对性能的影响可能是什么:
void set_flag(struct mystruct *sp)
{
if (sp->flag == 0U)
{
sp->flag = 1U;
}
}
Run Code Online (Sandbox Code Playgroud)
我希望避免写入主内存.第一个版本总是执行写操作,第二个版本只执行写操作(如果尚未设置标志),但在绝大多数情况下,标志将已设置.
还有哪些其他因素(例如分支预测)可能会影响性能?
到目前为止,我看到了一个小的速度增加,我希望随着数据集变大,这将变得更加重要.
是否有这种变化的风险使得大型数据集的程序变慢,如果是这样,在什么情况下会发生这种情况?
在这个链接上,我遇到了
http://lxr.linux.no/#linux+v2.6.36/include/linux/pci.h#L299
整数声明
unsigned int is_added:1;我已经制作了C程序并声明了整数,但在上面我看到了使用
:那
是什么语法?
OpenCL语言不支持位域.不支持他们的原因是什么?与其他忽略的部分(递归,函数指针,......)不同,有明显的理由不支持它们,我没有看到一个用于位域.我确信这不是代表委员会的疏忽,但是原因是什么?
(我存储了一些打包在int中的位,并且代码可以更好地与它们一起读取.我理解bitfields是一种很好的语法,可以避免位移和来回屏蔽,无论如何它们都是在汇编中转换的.)
我只想知道以下结构声明.哪一个更适合用于内存分配?为什么?那么在unsigned char和unsigned int的情况下填充呢?
struct data{
unsigned char a:3;
unsigned char b:4;
};
Run Code Online (Sandbox Code Playgroud)
和
struct data{
unsigned int a:3;
unsigned int b:4;
};
Run Code Online (Sandbox Code Playgroud) 在C++ 11中,人们可以做到
struct S {int i = 42;};
Run Code Online (Sandbox Code Playgroud)
每当忘记初始化成员i时,它会默认初始化为42.我只是尝试使用bitfields作为
struct S {int i = 42 : 5;};
Run Code Online (Sandbox Code Playgroud)
而且我正在
错误:预期';' 在':'标记之前
对于位域成员是否存在此功能,如果存在,我该如何使用它?
我正在尝试创建一个可变大小的颜色类 - 给定模板确定的值数组,我想为数组中的每个值创建命名别名,即:
template<int C = 3, typename T = unsigned char>
class Color {
public:
union {
T v[C];
struct {
T r, g, b, a;
};
};
};
Run Code Online (Sandbox Code Playgroud)
但是,如果我尝试为C = 3使用相同的类,则union要求4字节的大小('a'成员).或者,使用数学表达的位域大小((名为a,anonymous T成员的结构,大小在C> 3时评估为1),编译器发出一个允许警告(不可抑制,根据In gcc,如何静音 -敏感警告?),不适合大规模API的东西.
我如何允许单个类处理不同数量的变量,同时保留每个变量名称而不实现递归包含宏魔法(试过这个,不应该).提前致谢!
编辑:为了澄清问题,以下任何一个答案将解决此问题:
我有一个由微控制器制造商提供的寄存器定义,可以作为位字段处理.寄存器定义如下:
#define SCU_WDTSCON0 (*( SCU_WDTSCON0_type *) 0xf00360f0u)
Run Code Online (Sandbox Code Playgroud)
位字段定义如下所示:
typedef volatile union {
unsigned U;
int I;
struct {
unsigned ENDINIT :1; // [0:0] End-of-Initialization Control Bit
unsigned LCK :1; // [1:1] Lock Bit to Control Access to WDTxCON0
unsigned HPW0 :2; // [3:2] Hardware Password 0
unsigned HPW1 :4; // [7:4] Hardware Password 1
unsigned PW :8; // [15:8] User-Definable Password Field for Access to WDTxCON0
unsigned REL :16; // [31:16] Reload Value for the WDT
} B;
} SCU_WDTSCON0_type; …Run Code Online (Sandbox Code Playgroud) 我有一个64位长的int,其中包含一些位域.我需要在第二个和第三个字节中存储一个16位有符号的int并将其添加到32位值.我正在使用这样的东西:
u32 Function( s32 value , u64 bitfield )
{
return value + (s16) (bitfield >> 8)
}
Run Code Online (Sandbox Code Playgroud)
我可以依赖编译器将位域转换为16位带符号的int,然后再将其扩展为32位带符号的int并执行添加吗?如果没有,我应该如何截断剩余的字节并执行我需要的类型转换?
我有以下系列的结构.
struct FooWord1
{
unsigned int Fill : 8;
unsigned int someData1 : 18;
unsigned int someData2 : 6;
};
struct FooWord2
{
unsigned int Fill : 8;
union
{
unsigned int A_Bit : 1;
unsigned int B_Bit : 1;
};
unsigned int someData3 : 23;
};
struct Foo_Data
{
FooWord1 fooWord1;
FooWord2 fooWord2;
FooWord3 fooWord3; // similar to FooWord1
FooWord4 fooWord4; // similar to FooWord1
FooWord5 fooWord5; // similar to FooWord1
};
Foo_Data fooArray[SIZE];
Run Code Online (Sandbox Code Playgroud)
数据fooArray从网络消息逐字节复制.someData3如果我们不使用带有1位字段( …
问题在下面的代码中,询问使用的值初始化语法是否意味着对于各个位字段成员是零初始化还是未初始化:
struct S { // S is POD
int a : 3;
int b : 1;
};
S s1;
S s2{};
s1.a; // uninitialized (ok, we understand this)
s1.b; // "
s2.a; // zero or junk?
s2.b; // "
Run Code Online (Sandbox Code Playgroud)
以下是位域的复习:https://en.cppreference.com/w/cpp/language/bit_field
为具有许多位字段的结构创建归零构造函数通常使用遗留代码中的丑陋memset来完成,因为在构造函数初始化列表中使用value-init语法重复每个位域成员的名称会产生无法管理的代码.即使结构是用于良好测量的POD,也可以完成此操作.想要在C++ 11中尽可能消除这种情况(不幸的是,默认成员初始化语法不适用于位字段,直到C++ 20).C++ 11是否使用{} -init语法保证对此进行零初始化?