洛谷 P1147 連續自然數和 C

2021-10-23 10:37:39 字數 1195 閱讀 6484

1、題目(**於洛谷):

2、主要思想:

方法一:

①先想到雙重迴圈暴力列舉

②發現可以將列舉區間右端縮小為m的一半,因為從m / 2 + (m / 2 + 1)開始後面都會大於m

③又發現因為可以用雙指標,當列舉到s[j] - s[i - 1] == m或者s[j] - s[i - 1] > m時可以直接跳出迴圈,列舉下乙個 i 。

④用字首和優化計算子串行和的部分

方法二:

用代數方法根據數列前n相項合公式,發現(l + r)* (r - l + 1) / 2 = m。

設k1 = l + r, k2 = r - l + 1,可得r = (k1 + k2 - 1) / 2, l = (k1 - k2 + 1) / 2;(l + r)* (r - l + 1) = 2 * m。

因為l 和 r 均為整數而k1 + k2 = 2 * r + 1(奇數)所以k1 和k2 一定一奇一偶;因為 l != r 所以 (k1 + k2 - 1) / 2 != (k1 - k2 + 1) / 2, 可得k2 != 1。

將問題轉化為列舉k1,k2

3、c++**如下:

方法一:

#include

using

namespace std;

const

int n =

1000010

;int m;

int s[n]

;//s為字首和陣列

intmain()

if(s[j]

- s[i -1]

> m)

break

;//當s[j] - s[i - 1]已經大於 m 時,j再+1的話,序列和一定會大於m,後面不必再列舉}}

return0;

}

方法二:

#include

#include

using

namespace std;

intmain()

}return0;

}

注意事項:

題中m從10開始,對0似乎沒有特殊要求(感覺0 4和1 4都能得10),但是算上0又不能ac,就直接從1開始了。

洛谷P1147 連續自然數和

連續自然數和 題目描述 對乙個給定的自然數m,求出所有的連續的自然數段,這些連續的自然數段中的全部數之和為m m 2000000 例子 1998 1999 2000 2001 2002 10000,所以從1998到2002的乙個自然數段為m 10000的乙個解。分析可以把連續自然數段看成乙個等差數列...

洛谷 P1147 連續自然數和

對乙個給定的自然數m,求出所有的連續的自然數段,這些連續的自然數段中的全部數之和為m。例子 1998 1999 2000 2001 2002 10000,所以從1998到2002的乙個自然數段為m 10000的乙個解。包含乙個整數的單獨一行給出m的值 10 m 2,000,000 每行兩個自然數,給...

洛谷 P1147 連續自然數和

前言 只為轉c 而寫個解題報告。題目描述 對乙個給定的自然數m,求出所有的連續的自然數段,這些連續的自然數段中的全部數之和為m。例子 1998 1999 2000 2001 2002 10000,所以從1998到2002的乙個自然數段為m 10000的乙個解。輸入格式 包含乙個整數的單獨一行給出m的...