【问题标题】:Sum in loop not displaying actual result?循环求和不显示实际结果?
【发布时间】:2019-09-19 16:36:46
【问题描述】:

我应该对所有自然数的平方求和,直到它到达某个输入,但结果变得比它应该的要大。当我将 3 设置为输入时,结果变为 3*10⁹ 左右,请问我是否遗漏了数据类型或操作的错误?

顺便说一句,什么时候使用函数比在主代码中编写任何内容更有效?我对何时应该或不应该使用它们有很多疑问。

感谢任何可能阅读它的人。

#include <iostream>
using namespace std;

int main(){
    int input, sum;
    cin >> input;
    for(int i = 1; i <= input; i++){
        sum += i*i;
    }
    cout << sum << endl;
}

【问题讨论】:

  • sumint input, sum; 行之后的值是多少?因为您在 sum += i*i; 之前从未分配它,它会在添加之前读取 sum 的值。
  • 也就是说先初始化sum
  • 应该是0,是sum声明唯一的错误吗?
  • 似乎是,是的。
  • 我会选择 sum = 0 而不是 sum = o。

标签: c++ loops for-loop variables initialization


【解决方案1】:

您应该使用0 初始化变量sum,然后程序将成功运行。当你使用sum 而不初始化它时,你的程序的行为是undefined

您也可以使用下面的公式代替 for 循环:

sum = n * (n + 1) * (2 * n + 1) / 6

【讨论】:

  • 感谢您指出封闭式解决方案。这是迄今为止我认为最好的答案。投赞成票。
【解决方案2】:

你永远不会初始化sum,所以不能保证值从0开始。事实上,它的初始值本质上是未定义的。您只需在 for 循环之前添加行 sum = 0;

#include <iostream>
using namespace std;

int main(){
    int input, sum;
    sum = 0;
    cin >> input;
    for(int i = 1; i <= input; i++){
        sum += i*i;
    }
    cout << sum << endl;
}

“顺便说一句,什么时候使用函数比在主代码中编写任何东西更有效率”

它不一定更高效,但对于较大的项目,当常用功能被分组为可重用函数时,更容易阅读代码。作为一般经验法则,如果您多次编写相同的代码/算法,则应该为该代码/算法编写一个函数。

注意 - 正如其他人指出的那样,恰好有一个公式可以计算没有循环的平方和。

sum = n * (n + 1) * (2 * n + 1) / 6

这就是所谓的1 阶O(1) 解决方案,因为可以执行单个原子操作来实现您正在寻找的结果。另一方面,循环解被认为是 n 阶O(n),因为必须执行循环的n 迭代才能获得例程的结果。 O(1) 解决方案被认为是最佳的。如果您使用较大的值作为输入,那么您将明白原因。但是,如果您是编程新手,那么您的老师不会期望您对算法分析了解很多,上面的原始解决方案应该没问题。

【讨论】:

  • 那么如果我可以在一个循环中完成,是否需要编写函数?
  • 函数在编写代码时有其用处。在此示例中,函数不一定有用。如果main 中的代码变得很长,或者如果您在可以抽象为可重用函数时重复相同的代码,那么使用函数来组织、清晰和代码重用将是一个好主意。跨度>
【解决方案3】:

有两种方法可以解决您的问题。

第一个是将变量sum的声明放在main之前。例如

#include <iostream>
using namespace std;

int sum;

int main(){
    int input;
    cin >> input;
    for(int i = 1; i <= input; i++){
        sum += i*i;
    }
    cout << sum << endl;
}

在这种情况下,变量将具有静态存储持续时间,并将由编译器初始化为 0。

否则变量具有自动存储持续时间,必须像这样显式初始化

#include <iostream>
using namespace std;

int main(){
    int input, sum = 0;
    cin >> input;
    for(int i = 1; i <= input; i++){
        sum += i*i;
    }
    cout << sum << endl;
}

请注意,最好将变量声明为 long long int 类型,因为平方和可能太大,不适合 int 类型的对象。例如

#include <iostream>
using namespace std;

int main(){
    int input;
    long long int sum =0;
    cin >> input;
    for(int i = 1; i <= input; i++){
        sum += ( long long int )i*i;
    }
    cout << sum << endl;
}

【讨论】:

  • 这是一个很好的透彻分析(和往常一样),但你为什么忽略了封闭形式的解决方案?
  • @Bathsheba 你是什么意思?
  • 使用 bss 技巧将 sum 初始化为 0 很聪明,但在这种情况下似乎有点懒惰,如果这是一个新程序员,它只会让他们感到困惑,甚至会失去教授的分数.
  • @VladfromMoscow: sum = input * (input + 1) * (2 * input + 1) / 6.
  • @VladfromMoscow:确实,但是如果存在一种 O(1) 方式,那么您的责任就是指出。请记住,答案不一定针对 OP。
【解决方案4】:

您没有初始化sum。因此,每当您执行 sum += i * i 时,您就是在向垃圾值添加数字。
这就是您得到错误结果的原因。
要解决此问题,只需将 int input, sum; 替换为 int input, sum(0);

【讨论】:

    猜你喜欢
    • 2020-06-09
    • 2015-06-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-12-23
    • 2017-01-04
    • 2014-07-13
    • 1970-01-01
    相关资源
    最近更新 更多