C(HW)中的逐位饱和加法

问题描述 投票:7回答:2

我正在完成一项任务,我无法弄清楚如何实现这一点。我必须创建一个函数sadd(int x, int y),它返回加在一起的数字,除非它溢出(然后只返回max possible int)。我已经能够提出一些涉及强制转换和条件语句的解决方案,但解决方案中不允许这些解决方案。只有运营商~ ! ^ + << >> &|

c bit-manipulation addition saturation-arithmetic
2个回答
6
投票

对于添加有符号数字,如果添加两个相同符号的数字并使用不同的符号得到结果,则会发生溢出。由于涉及的范围,在添加两个不同的符号时不可能产生溢出。

那么,你可以做的是 - 只观察符号位(二进制补码中最重要的一位) - 使用异或来判断两个原始数字是否有不同的符号,补充这一点以便你得到'0'如果他们是不同的,同样的'1'。

然后,您可以对结果与其中一个输入使用异或。如果它们是相同的那么'0',如果它们不同则给'1'。

如果两个输入相同但结果不同,则这两个结果一起得到总体'1',否则为'0'。

然后,您可以使用移位和OR的组合来使用该值填充整个整数。假设您是32位整数,只需设置最低31位以获得最高值正整数。然后你可以做的是在任一输入的符号位上进行类似的移位和OR运算。独家OR结果。如果输入为负,那么它将给出最小值整数。

编辑:哦,并使用是否存在溢出的位值,扩展为填充int,选择返回的值,并将结果返回,如果有溢出则返回,补充它并将其与正常值一起使用加性结果,然后将两者结合在一起(或加入)。

Presto:所有二进制逻辑,无条件。我假设,因为它是家庭作业,你不想要实际的代码?


0
投票

来自ARM网站的内在功能:

4.1编译器内在函数

编译器内在函数是编译器提供的函数。它们使您能够轻松地将特定于域的操作合并到C和C ++源代码中,而无需使用汇编语言中的复杂实现。 C和C ++语言适用于各种各样的任务,但它们不为特定的应用领域提供内置支持,例如,数字信号处理(DSP)。在给定的应用程序域中,通常需要经常执行一系列特定于域的操作。但是,这些操作通常无法在C或C ++中有效实现。一个典型的例子是两个32位有符号二进制补码整数的饱和加法,通常用于DSP编程。以下示例显示饱和添加操作的C实现

#include <limits.h>
int L_add(const int a, const int b)
{
    int c;
    c = a + b;
    if (((a ^ b) & INT_MIN) == 0)
    {
        if ((c ^ a) & INT_MIN)
        {
            c = (a < 0) ? INT_MIN : INT_MAX;
        }
    }
    return c;
}

ARM Info Center

© www.soinside.com 2019 - 2024. All rights reserved.