回答編集履歴

2

mはグローバル変数なので初期値は0だった

2024/07/09 21:09

投稿

actorbug
actorbug

スコア2343

test CHANGED
@@ -23,7 +23,7 @@
23
23
  }
24
24
 
25
25
  double inv(double N, int x) {
26
- double L = 0, R = 100, m;
26
+ double L = 0, R = 100, m = 0;
27
27
  for (int i = 0; i < x; i++) {
28
28
  m = (L + R) / 2;
29
29
  if (N < f(m)) R = m;

1

ループ回数の計算方法の提示

2024/07/09 21:05

投稿

actorbug
actorbug

スコア2343

test CHANGED
@@ -10,3 +10,44 @@
10
10
  cout << setprecision(8) << m << endl;
11
11
  ```
12
12
  こちらで試すと、「x >= 25で機能する」というのも変わってくると思います。
13
+
14
+ ### 追記
15
+
16
+ ご提示のコードの場合、初期状態で入り込む可能性のある絶対誤差の最大値は100で、ループを1回回すごとにその最大値が半分になります。ループ17回目で0.00076...となり0.001を下回るので、17回やれば確実に問題の条件を満たせます。ただし、ここで求めた値はあくまで絶対誤差の最大値ですし、問題では相対誤差0.001も許容するので、実際にはループ16回で題意を満たす回答となります(以下のコードで確認)。
17
+ ```c++
18
+ #include <bits/stdc++.h>
19
+ using namespace std;
20
+
21
+ double f(double m) {
22
+ return m * m * m + m;
23
+ }
24
+
25
+ double inv(double N, int x) {
26
+ double L = 0, R = 100, m;
27
+ for (int i = 0; i < x; i++) {
28
+ m = (L + R) / 2;
29
+ if (N < f(m)) R = m;
30
+ else L = m;
31
+ }
32
+ return m;
33
+ }
34
+
35
+ bool valid(int x) {
36
+ for (int N = 1; N <= 100000; ++N) {
37
+ double m = inv(N, x);
38
+ if (!(f(m - 0.001) <= N && N <= f(m + 0.001) || f(m / 1.001) <= N && N <= f(m / 0.999)))
39
+ return false;
40
+ }
41
+ return true;
42
+ }
43
+
44
+ int main() {
45
+ int ok = 50, ng = 0;
46
+ while (ok - ng > 1) {
47
+ int mid = ng + (ok - ng) / 2;
48
+ if (valid(mid)) ok = mid;
49
+ else ng = mid;
50
+ }
51
+ cout << ok << endl;
52
+ }
53
+ ```