Как создать макрос для обратного порядка битов в ячейках массива

Я пытаюсь создать макрос в c, целью которого является перезапись в обратном порядке битов каждой ячейки в массиве, например, если ячейка A[1] равна: 1100, последняя ячейка A[1] будет: 0011 .

Я создал макрос, но у меня проблема с компиляцией. Пожалуйста, дайте мне знать, если я ошибся (я уверен, что это может выглядеть более компактно, но я не хочу знать, что мне не хватает).

#include <stdio.h>


#define REVERSE(array, type) \
(   \
    type * p; \
    unsigned (type)=mask1, mask2, test;\
    mask1=1;\
    mask2=mask1<<(sizeof(type)-1);\
    for(p=(array);p ;p=p+1){\
        while((mask1=<<1)<(mask2=>>1)){\
            if(((*p)&mask1)!=((*p)&mask2)){\
                if((*p)&mask1==0){\
                    *p=*p|mask1;\
                    *p=*p^mask2;\
                }else{\
                    *p=*p^mask1;\
                    *p=*p|mask2;\
                }\
            }\
        } \
)   
int main(){
int i;
int array[]= {1,2,3,4,5};
REVERSE((array), int);
for(i=1; i<5; i++)
    printf(" \'%d\' ", array[i]);
return(0);
}

person Julya Levin    schedule 29.06.2015    source источник
comment
Скомпилируйте с -E (gcc), чтобы проверить расширенный код C. В общем, не очень хорошая идея, чтобы макрос создавал такую ​​сложную функцию. Обратите внимание, что код вполне может быть плохо оптимизирован. Многие современные процессоры имеют отдельные инструкции для реверсирования битов uint32_t или uint64_t. Это, вероятно, в 100 раз быстрее, чем ваш подход.   -  person too honest for this site    schedule 29.06.2015
comment
Вы не указали, в чем ошибка. И почему вы пишете это как макрос?   -  person Carcigenicate    schedule 29.06.2015


Ответы (2)


Я бы предложил использовать для этого поисковый массив. Если размер типа больше, чем char, вы можете использовать поиск байта, а затем переместить байты в правильное место. Если вы не будете возиться с битами, ваш код будет работать быстрее. Массив символов (байт) длиной 256 является тривиальным размером. Ответ Роберта Картайно перестановка битов на месте в массиве покажет вам, что я имею в виду. Я думаю, что его массив может быть коротким, так как я ожидаю, что замена 0xff будет 0xff. Его массив заканчивается на 0x7F.

person Robert Jacobs    schedule 29.06.2015

#define REVERSE(arr,sz,type)               \
{                                          \
    size_t i;                              \
    for(i=0; i<(sz); i++) {                \
        type v1 = (arr)[i], v2 = 0;        \
        size_t j;                          \
        for(j=0; j<8*sizeof(type); j++) {  \
            v2 = (v2 << 1) | (v1 & 1);     \
            v1 >>= 1;                      \
        }                                  \
        (arr)[i] = v2;                     \
    }                                      \
}

Примечание. Я добавил аргумент sz, чтобы указать длину массива. В вашем коде цикл for for(p=(array); p ;p=p+1) будет работать для строки C, но не для любого числового массива.

person fferri    schedule 29.06.2015