【问题标题】:runtime error: signed integer overflow: 99998 * 100000 cannot be represented in type 'int' [solution.c]运行时错误:有符号整数溢出:99998 * 100000 无法以“int”类型表示 [solution.c]
【发布时间】:2021-05-28 15:03:33
【问题描述】:

尝试解决https://leetcode.com/problems/k-concatenation-maximum-sum/submissions/,当数据类型为long时,我还是出现整数溢出

#include <stdlib.h>
#include <stdio.h>
#include <math.h>

int max(int a, int b) {
    return a > b ? a : b;
}

int sum(int *nums, int numSize) {
    int ans = 0;
    for (int i = 0; i < numSize; ++i)
        ans += nums[i];
    return ans;
}

int KandaneAlgo(int *nums, int numSize) {
    int i, max_overall_so_far = 0, max_ending_here = 0;
    for (i = 0; i < numSize; ++i) {
        max_ending_here += nums[i];
        if (max_ending_here < 0)
            max_ending_here = 0;
        if (max_overall_so_far < max_ending_here)
            max_overall_so_far = max_ending_here;
    }
    return max_overall_so_far;
}

int kConcatenationMaxSum(int *arr, int arrSize, int k) {
    int mod = pow(10, 9) + 7;
    int ans;
    if (k > 1) {
        long tem = (k - 2) * max(sum(arr, arrSize), 0);
        int t1 = tem % mod;
        printf("%ld, %d, %d \n", tem, t1, mod);
        int arr2[2 * arrSize];
        for (int i = 0; i < 2 * arrSize; ++i)
            arr2[i] = arr[i - i / arrSize * arrSize];
        ans = (int)t1 +  KandaneAlgo(arr2, 2 * arrSize) % mod;
    } else {
        ans = KandaneAlgo(arr, arrSize) % mod;
    }
    return ans;
}

int main() {
    int arr[10] = { [0 ... 9] = 10000 };
    for (int i = 0; i < 10; ++i)
        printf("%d ", arr[i]);
    printf("\n");
    int tot = kConcatenationMaxSum(arr, 10, 100000);
    printf("%d \n", tot);
    return 0;
}

我用lldb本地调试,可以看到变量tem的输出信息确实不对,应该是9999800000

【问题讨论】:

  • 错误在哪一行?
  • @RetiredNinja long tem = (k - 2) * max(sum(arr, arrSize), 0);
  • k - 2 是一个 int,max 返回一个 int。不管你分配什么,如果你需要用 long 完成数学运算,那么一侧或两侧必须是 long 或强制转换为一个。
  • 同样 long 不一定是 8 个字节。取决于系统。使用 long long 以确保安全。或者提高专业水平,开始使用 stdint.h 而不是原始类型。
  • @RetiredNinja 太棒了,谢谢!

标签: c overflow


【解决方案1】:

这是因为9999800000 比 32 位可以存储的要大。 long 仅提供32 位的最小大小保证。如果您对表达式中的所有操作数和结果变量使用long long,它的计算结果是正确的值。 long long 提供最低 64 位保证。
检查此以获取更多详细信息 - https://en.wikipedia.org/wiki/C_data_types#Main_types

以下 sn-p 对我有用:

long long tem = (long long)(k-2) * (long long)max(sum(arr, arrSize), 0);

不确定算法的其余部分,但这会将正确的值放入tem

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-10
    • 1970-01-01
    • 2012-02-29
    相关资源
    最近更新 更多