C 使用结构/联合组合
我在PIC18F87K90微控制器中使用c编程。我在创建一个结构变量(其中包含union)以便更容易地访问多个标志(大多数是1位标志,但有些是2位或3位标志)时遇到了一个问题 下面的代码运行良好。我使用模拟器检查每个成员的地址字节。union中的结构成员被分组在同一地址字节中,我希望这样,因为这些成员总共有8位,应该适合1字节。我还检查了以下地址: eeprom_标志。字节0,eeprom_标志。重置时间_字节。。。由于工会惯例,他们在同一地址。 我的问题是,我希望1位标志中的一个有两个可能的名称,即eeprom_flag.output_time_bit。我想给它取另一个名字(但完全相同的变量位,相同的地址)。我尝试使用union来实现这一点(请参见下面的注释行)。但是,这样做会破坏我的代码,使结构的成员不再位于相同的地址中。我的目标是完成上传图像中显示的寻址C 使用结构/联合组合,c,pic,pic18,C,Pic,Pic18,我在PIC18F87K90微控制器中使用c编程。我在创建一个结构变量(其中包含union)以便更容易地访问多个标志(大多数是1位标志,但有些是2位或3位标志)时遇到了一个问题 下面的代码运行良好。我使用模拟器检查每个成员的地址字节。union中的结构成员被分组在同一地址字节中,我希望这样,因为这些成员总共有8位,应该适合1字节。我还检查了以下地址: eeprom_标志。字节0,eeprom_标志。重置时间_字节。。。由于工会惯例,他们在同一地址。 我的问题是,我希望1位标志中的一个有两个可能的名
typedef struct
{
//buffer index 0
union
{
struct
{
uint8_t reset_time_bit:1;
// union
// {
uint8_t output_time_bit:1; //shared address
// uint8_t output2_time_bit:1;
// };
uint8_t count_mode_bit:3;
uint8_t input_mode_bit:1;
uint8_t count_speed_bit:2;
};
uint8_t byte0;
uint8_t reset_time_byte;
uint8_t output_time_byte;
uint8_t output2_time_byte;
uint8_t count_mode_byte;
uint8_t input_mode_byte;
uint8_t count_speed_byte;
};
} eeprom_flag_t;
extern volatile eeprom_flag_t eeprom_flag;
虽然我不明白您为什么要这样做,但以下内容可能会满足您的要求 其思想是定义2位字段(
struct
),这些字段以一种您喜欢的方式重叠(union
)
union
{
struct { uint8_t output_time_bit:1;} ;
struct { uint8_t output2_time_bit:1;} ;
}
从理论上讲,您想要的可能是可能的,但在实践中,没有一家供应商编写过能够做到这一点的编译器。通常,联合与字节边界对齐。在某些编译器上,它们与2、4、8或16字节边界对齐 您必须重新声明整个结构才能实现您想要的。不需要在结构中放置联合-该联合可以直接在typedef中使用)。此外,如果不命名内部结构,则可能无法在调试器中查看值。调试器对此喜怒无常——有时你可以,有时你不能
typedef union
{
struct
{
uint8_t reset_time_bit:1;
uint8_t output_time_bit:1; //shared address
uint8_t count_mode_bit:3;
uint8_t input_mode_bit:1;
uint8_t count_speed_bit:2;
} bits1;
struct
{
uint8_t reset_time_bit:1;
uint8_t output2_time_bit:1;
uint8_t count_mode_bit:3;
uint8_t input_mode_bit:1;
uint8_t count_speed_bit:2;
} bits2;
uint8_t byte0;
...
} eeprom_flag_t;
或者,正如@Mike所建议的,只需使用一个结构,然后#定义另一个结构的位字段
通常,如果使用|和&,编译器将生成较少的代码。除了or和ing之外,使用位还会产生大量的左右移位。
查看生成的代码时,您可能会很快感到困惑。联合的最小大小是一个字节。你不能实现你所追求的。使用包含位字段和其他名称之一的结构的并集有一定的意义。为8位值指定7个(而不是1个)名称没有什么明显的好处。可能:
#定义output2\u time\u bit output\u time\u bit
Thx以获取建议。关于不使用#define、#ifdef、#endif,使用output2_time_位还是output2_time_位的决定将在我的微控制器初始化后做出,因此从技术上讲它是在运行时,尽管只是在初始化时。