让我们说我在c的部分代码中有这个2D数组:
unsigned short testing[5][3];
然后我将数据插入其中,并让我们对其进行监控
testing[0][0] = 00110010;
testing[0][1] = 01101001;
testing[0][2] = 11100001;
实际上,如果我们监视数组的第一个下标(使用调试工具进行监视)
testing[0] = 001100100110100111100001; /*which is combination of 3 second subscript of the array*/
问题是我如何才能将2D数组向左移一位
让我们说我希望得到这个输出
Original :
testing[0][0-2] = 001100100110100111100001;
The output I wish :
testing[0][0-2] = 011001001101001111000010;
我这样做的方法尚未完成,但我认为有另一种明智的方法可以在这里询问
for(int i = 0; i<5; i++)
{
for(int j = 0; j < 3; j++)
{
testing[i][j] <<= 1;
/*I believe here will cause the padding first bit disappear also*/
}
}
如果是普通数组(或者可以说一维数组),我确实知道可以很容易地通过
int a[2];
a[0] <<= 1;
但是在2D数组中,任何人都可以提出建议,也许有一些简单的方法可以移动第一个下标的位?
要明确地说,我的问题是,是否可以移动2D数组的第一个下标?
答案 0 :(得分:0)
void shiftleft(uint16_t *data, size_t nwords)
{
data[nwords - 1] <<= 1;
for(size_t index = nwords - 1; index > 0; index--)
{
uint32_t tmp;
tmp = data[index - 1] << 1;
data[index] |= !!(tmp & (1UL << 16));
data[index - 1] = tmp & 0xffff;
}
}
最初的问题是第二个索引是3
,您可以使用位域/联合组合。
typedef union
{
struct
{
uint64_t d48: 48;
uint64_t : 16;
};
uint64_t d64;
uint16_t d16[4];
}Data48;
void shiftleft(uint16_t *data)
{
Data48 d48;
d48.d16[0] = *data++;
d48.d16[1] = *(data+1);
d48.d16[2] = *(data+2);
d48.d48 <<= 1;
*data++ = d48.d16[0];
*(data+1) = d48.d16[1];
*(data+2) = d48.d16[2];
}
您只需将其更改为您的字节序
答案 1 :(得分:0)
作为开场白,我希望C支持8080 / Z80上存在的某些位操作,并且可能也可以在x86上使用。特别是,使用Z80来称呼RLC
指令。
与OP问题相关的是RLC
是专门为解决这一确切问题而设计的:移位/旋转多字节值。记住这一点,您可以使用C中可用的操作来实现相同的结果。这只是花了一点功夫。
void arrayshift(unsigned short *array, size_t elementCount)
{
int carry = 0;
size_t i;
for (i = 0; i < elementCount; i++)
{
// This assumes 8 bit bytes and sizeof(short) == 2. Adjust as needed if this is not the case
int newCarry = *array >> 15;
*array = *array << 1 | carry;
carry = newCarry;
array++;
}
}
总而言之,如果编译器支持它,并且愿意将可移植性抛诸脑后,则可以退回到汇编器并尝试使用目标CPU上可用的指令来有效地做到这一点。
这是一个决定,必须视具体情况而定,所以我仅将其列为可能的选择,而不是答案。