【问题标题】:Sum of different numbers in an array数组中不同数字的总和
【发布时间】:2016-11-22 09:18:55
【问题描述】:

我想要一个从数组中返回不同(非重复)值总和的函数:如果我有{3, 3, 1, 5},我想要有3 + 1 + 5 = 9 的总和。

我的尝试是:

int sumdiff(int* t, int size){
    int sum=0;
    for (int i=0; i<=size;i++){
        for(int j=i; j<=size;j++){
            if(t[i]!=t[j])
            sum=sum+t[i];
        }
    }
    return sum;
}

int main()
{
    int t[4]={3, 3, 1, 5};
    cout << sumdiff(t, 4);
}

它返回25,我想我知道为什么,但我不知道如何改进它。我应该改变什么?

【问题讨论】:

  • 请在问题中解释您的“为什么”(您说您认为您知道它为什么不起作用)。此外,格式化您的代码,使其更具可读性。
  • (1) 你超出了数组的范围; (2) 您正在比较索引而不是元素的值以进行重复检查。
  • 你有未定义的行为,超出了数组的访问范围
  • 现在我想我正在比较这些值。

标签: c++ loops


【解决方案1】:

将所有项目放在一组中,然后计数。

集合是只包含每个值的一个元素的数据结构(即,它们的每个元素都是唯一的;如果您尝试多次添加相同的值,则只会计算一个实例)。

您可以在this interesting question 中查看有关为 int 执行此操作的最优雅方式。

【讨论】:

  • 也许扩大你的答案一点?
  • 我将不胜感激。
  • 哇,这真是太快了,迈克 :)
  • 我已经详细说明了,HTH。
  • 但它可以以类似于我想做的方式完成吗?
【解决方案2】:

首先,您的循环应该是for (int i=0; i&lt;size;i++)。您的实际代码超出了数组的范围。

然后,如果你不想使用 STL 容器和算法(但你应该),你可以修改你的代码如下:

int sumdiff(int* t, int size){
    int sum=0;
    for (int i=0; i<size;i++){

        // check if the value was previously added

        bool should_sum = true;

        for(int j=0; should_sum && j<i;j++){
            if(t[i]==t[j])
                should_sum = false;
        }

        if(should_sum)
            sum=sum+t[i];
    }
    return sum;
}

int main()
{
    int t[4]={3, 3, 1, 5};
    cout << sumdiff(t, 4);
}

【讨论】:

  • 还有一个问题,为什么 j
  • 直到 before 元素的索引 i
【解决方案3】:

你可以:

  • 首先将您的数组内容存储到std::unordered_set。通过这样做,您基本上可以自动删除重复项。
  • 然后调用std::accumulate计算总和
  • 【讨论】:

      【解决方案4】:

      **wasthishelpful 的回答正是我所说的。我发了我的帖子后才看到他的帖子。

      因此,您正在尝试使用内部循环检查重复号码。 但是,无论哪个给您错误的结果,您的外部循环都会循环 4 次。 试试吧,

      • 只检查内部循环。 (如果为假则使用标志记录)
      • 在内循环之外进行求和。 (当标志为真时求和)

      【讨论】:

        【解决方案5】:

        这是使用std::accumulate 的另一种解决方案,但它在对std::accumulate 的调用中迭代原始元素,并构建集合并在遇到数组中的每个数字时保持运行总计:

        #include <iostream>
        #include <numeric>
        #include <set>
        
        int main()
        {
            int t[4] = { 3, 3, 1, 5 };
            std::set<int> mySet;
            int mySum = std::accumulate(std::begin(t), std::end(t), 0, 
                 [&](int n, int n2){return n += mySet.insert(n2).second?n2:0;});
            std::cout << "The sum is: " << mySum << std::endl;
            return 0;
        }
        

        它的工作方式是std::insert() 将返回一个pair tbat 确定该项目是否已插入。该对的second 是一个bool,表示该项目是否已插入集合中。如果插入成功,我们只添加到总数中,否则我们添加0

        Live Example

        【讨论】:

        • const std::set&lt;int&gt; mySet{std::begin(t), std::end(t)}; const int mySum = std::accumulate(std::begin(t), std::end(t), 0); 似乎更自然/更简单。
        【解决方案6】:

        将数组元素插入集合并使用std::accumulate函数:

        #include <iostream>
        #include <numeric>
        #include <set>
        
        int main()
        {
            int t[4] = { 3, 3, 1, 5 };
            std::set<int> mySet(std::begin(t), std::end(t));
            int mySum = std::accumulate(mySet.begin(), mySet.end(), 0);
            std::cout << "The sum is: " << mySum << std::endl;
            return 0;
        }
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2020-07-17
          • 2012-03-11
          • 1970-01-01
          • 2022-12-03
          • 2023-01-03
          • 2016-05-17
          • 2012-09-29
          • 1970-01-01
          相关资源
          最近更新 更多