абсолютное значение разницы между двумя символами в таблице ASCII без «abs» или «if» - PullRequest
0 голосов
/ 25 ноября 2018

это мой код:

#include <stdio.h>
  void main() {
        char a, b;
        char c;
        printf("enter 2 chars: ");
        a = getchar();
        b = getchar();
        c = a - b;
        printf("%d",c );
  }

Я пытаюсь найти абсолютное значение между двумя символами, например, 'A' & 'a' => 32 'a' & 'A'=> 32 мой код показывает отрицательный ответ, что мне делать без использования функции abs или если, я попробовал это:

printf("%u",c );

, но это дает мне 4294967264. Есть ли какой-либо простой способсделать это?он должен использовать getchar и putchar!

Ответы [ 2 ]

0 голосов
/ 25 ноября 2018

Без ветвления: (предполагается, что два целых числа дополняют)

#include <stdio.h>

int main(void)
{
    printf("Enter 2 chars: ");
    char a = getchar();
    char b = getchar();
    char c = a - b;

    c = (c^-(c < 0)) + (c < 0);

    printf("%d\n", c);
}

Разделить на части:

(c < 0) дает 0, когда c положительно:c = (c^-0) + 0 ~> c = c^0 ... $ foo XOR 0 дает $ fooc = c ничего не делать.(c < 0) дает 1, когда c отрицательно:c = (c^-1) + 1 ... -1 в двух дополнениях установлены все биты (~0)c = (c^(~0)) + 1 ... отрицательный c в дополнительном коде XOR ~0 дает -c - 1c = -c - 1 + 1 ~> c = -c

gcc 8,3 -O3: (cl v15.9.0-pre.3.0 создает эквивалентную сборку)

mov     edx, edi    ; edx = c
shr     edx, 31     ; right shift, keep only the sign bit (c < 0) [sign]
mov     eax, edx    ; eax =  [sign]
neg     eax         ; eax = -[sign]
xor     eax, edi    ; eax = -[sign] xor c
add     eax, edx    ; eax += [sign]
0 голосов
/ 25 ноября 2018

Самый простой способ - использовать функцию abs.

printf("%d",abs(c) );

Но если вы не хотите ее использовать, вы можете попробовать изменить строку:

c = a - b;

на:

c = (a > b) ? (a-b) : (b - a);
...