xglow - 1 year ago 89

C++ Question

I'm a beginner in programming. I am trying to make a program that given two numbers it substracts one harmonic from the other. (Input: n, m / Output: Hn-Hm)

`#include <iostream>`

#include <iomanip>

#include <math.h>

using namespace std;

int main() {

double n1, n2, h1 = 0, h2 = 0, i; // n = number, h = harmonic

cin >> n1 >> n2;

if (n1 == 0) {

h1 = 0;

}

else {

for (i = 1; i <= n1; i++) {

h1 += 1 / i;

if (i <= n2) {

h2 += 1 / i;

}

}

}

cout << fixed << setprecision(10) << h1 - h2 << endl;

system("pause");

return 0;

}

The program gives correct results but I'm using a website of my university and it says that the program is slow. I've tried to make it faster but I can't figure out how.

Thanks.

Answer Source

You don't need to calculate the full harmonic numbers. Assuming `n1 < n2`

, the two series will be:

```
H(n1) = 1 + 1/2 + 1/3 + ... + 1/n1
H(n2) = 1 + 1/2 + 1/3 + ... + 1/n1 + 1/(n1+1) + 1(n1+2) + ... + 1/n2
```

So when you subtract `H(n2) - H(n1)`

, the first `n1`

terms in the two series cancel each other out, so

```
H(n2) - H(n1) = 1/(n1+1) + 1(n1+2) + ... + 1/n2
```

If `n1 > n2`

the result is the negative of this.

```
double result = 0, mult = 1;
if (n1 > n2) {
double temp = n1;
n1 = n2;
n2 = temp;
mult = -1;
}
for (double denom = n1+1; denom <= n2; denom++) {
result += 1/denom;
}
result *= mult; // Flip the sign if we swapped n1 and n2
cout << fixed << setprecision(10) << result << endl;
```