我的 for 循环增加了 +1 过量,我不知道为什么
My for loop is adding +1 excess and i do not know why
基本上,我正在尝试编写一个循环遍历给定数组的程序,并检查右侧元素是否比左侧元素大 2 倍,如果为真,则在中间插入这两个元素的平均值。之后,它打印出插入元素的数组,然后再次循环遍历数组,统计某个数字出现了多少次。我使用笔和纸成功地对所有这些进行了编码,并将问题写入较小的块,然后用 C 对其进行编码,但问题是当我输入 100 个零(一百个零)时。程序打印出数字 0 重复了 200 次而不是 199 次。我不知道为什么。很抱歉代码不好,我目前的任务是擅长用笔和纸解决问题,在我变得体面并发展我的逻辑之后,我会尝试使代码更简单。
Input sample:
Enter the number of elements: 100
Enter the array: 0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
After adding middle element: 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002.33412e-310
The number is repeated 200 time/s
我的代码
#include <math.h>
#include <stdio.h>
#define EPSILON 0.0001
int main() {
int n, i, j, k, digit, length = 0, digit_array[10] = {0};
double array[200], temp;
do {
printf("Enter number of elements: ");
scanf("%d", &n);
} while (n <= 0 || n >= 101);
printf("Enter elements: ");
length = n;
for (i = 0; i < length; i++)
scanf("%lf", &array[i]);
for (i = 0; i < length; i++) {
temp = array[i] + array[i];
if (fabs(temp - array[i + 1]) < EPSILON) {
for (j = length; j > i + 1; j--)
array[j] = array[j - 1];
array[i + 1] = (array[i] + array[i + 1]) / 2.;
i++;
length++;
}
}
printf("After adding middle element: \n");
for (i = 0; i < length; i++)
printf("%g ", array[i]);
for (i = 0; i < length; i++) {
temp = array[i];
digit = ((int)(temp * 10)) % 10;
digit_array[digit]++;
}
printf("\n");
for (i = 0; i < 10; i++) {
if (digit_array[i] != 0)
printf("Number %d is repeated %d time/s.\n", i, digit_array[i]);
}
return 0;
}
与不断移动数组相比,使用两个数组更容易、更快捷。你只需要这个:
// Inputs:
// n: The number of inputs.
// a: An array of at least n doubles containing the inputs.
// b: An array of at least n*2-1 doubles that will containing the outputs.
// Outputs:
// m: The number of outputs.
// b: An array of at least m doubles containing the outputs.
size_t i = 0;
size_t j = 0;
double prev = b[j++] = a[i++];
while (i < n) {
double next = a[i];
if (fabs(prev*2 - next) < EPSILON) { // If a[i-1] exactly equal a[i]*2.
b[j++] = next / 2.0 + prev / 2.0; // Or: b[j++] = prev * 1.5;
}
prev = b[j++] = a[i++];
}
size_t m = j;
关于prev * 1.5
:
average(next, prev)
= ( next + prev ) / 2
= ( prev * 2 + prev ) / 2
= ( prev * 3 ) / 2
= prev * 1.5
包含在适当的功能中:
int f(double *a, size_t n, double **b_ptr, size_t *m_ptr) {
double b = malloc( (n*2-1) * sizeof(double) ); // We need up to this much.
if (b == NULL) {
*b_ptr = NULL;
return 0;
}
size_t i = 0;
size_t j = 0;
double prev = b[j++] = a[i++];
while (i < n) {
double next = a[i];
if (fabs(prev*2 - next) < EPSILON) { // If a[i-1] exactly equal a[i]*2.
b[j++] = next / 2.0 + prev / 2.0; // Or: b[j++] = prev * 1.5;
}
prev = b[j++] = a[i++];
}
b = realloc(b, j * sizeof(double)); // Free the excess. (Optional)
size_t m = j;
*b_ptr = b;
*m_ptr = m;
return 1;
}
基本上,我正在尝试编写一个循环遍历给定数组的程序,并检查右侧元素是否比左侧元素大 2 倍,如果为真,则在中间插入这两个元素的平均值。之后,它打印出插入元素的数组,然后再次循环遍历数组,统计某个数字出现了多少次。我使用笔和纸成功地对所有这些进行了编码,并将问题写入较小的块,然后用 C 对其进行编码,但问题是当我输入 100 个零(一百个零)时。程序打印出数字 0 重复了 200 次而不是 199 次。我不知道为什么。很抱歉代码不好,我目前的任务是擅长用笔和纸解决问题,在我变得体面并发展我的逻辑之后,我会尝试使代码更简单。
Input sample:
Enter the number of elements: 100
Enter the array: 0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
After adding middle element: 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002.33412e-310
The number is repeated 200 time/s
我的代码
#include <math.h>
#include <stdio.h>
#define EPSILON 0.0001
int main() {
int n, i, j, k, digit, length = 0, digit_array[10] = {0};
double array[200], temp;
do {
printf("Enter number of elements: ");
scanf("%d", &n);
} while (n <= 0 || n >= 101);
printf("Enter elements: ");
length = n;
for (i = 0; i < length; i++)
scanf("%lf", &array[i]);
for (i = 0; i < length; i++) {
temp = array[i] + array[i];
if (fabs(temp - array[i + 1]) < EPSILON) {
for (j = length; j > i + 1; j--)
array[j] = array[j - 1];
array[i + 1] = (array[i] + array[i + 1]) / 2.;
i++;
length++;
}
}
printf("After adding middle element: \n");
for (i = 0; i < length; i++)
printf("%g ", array[i]);
for (i = 0; i < length; i++) {
temp = array[i];
digit = ((int)(temp * 10)) % 10;
digit_array[digit]++;
}
printf("\n");
for (i = 0; i < 10; i++) {
if (digit_array[i] != 0)
printf("Number %d is repeated %d time/s.\n", i, digit_array[i]);
}
return 0;
}
与不断移动数组相比,使用两个数组更容易、更快捷。你只需要这个:
// Inputs:
// n: The number of inputs.
// a: An array of at least n doubles containing the inputs.
// b: An array of at least n*2-1 doubles that will containing the outputs.
// Outputs:
// m: The number of outputs.
// b: An array of at least m doubles containing the outputs.
size_t i = 0;
size_t j = 0;
double prev = b[j++] = a[i++];
while (i < n) {
double next = a[i];
if (fabs(prev*2 - next) < EPSILON) { // If a[i-1] exactly equal a[i]*2.
b[j++] = next / 2.0 + prev / 2.0; // Or: b[j++] = prev * 1.5;
}
prev = b[j++] = a[i++];
}
size_t m = j;
关于prev * 1.5
:
average(next, prev)
= ( next + prev ) / 2
= ( prev * 2 + prev ) / 2
= ( prev * 3 ) / 2
= prev * 1.5
包含在适当的功能中:
int f(double *a, size_t n, double **b_ptr, size_t *m_ptr) {
double b = malloc( (n*2-1) * sizeof(double) ); // We need up to this much.
if (b == NULL) {
*b_ptr = NULL;
return 0;
}
size_t i = 0;
size_t j = 0;
double prev = b[j++] = a[i++];
while (i < n) {
double next = a[i];
if (fabs(prev*2 - next) < EPSILON) { // If a[i-1] exactly equal a[i]*2.
b[j++] = next / 2.0 + prev / 2.0; // Or: b[j++] = prev * 1.5;
}
prev = b[j++] = a[i++];
}
b = realloc(b, j * sizeof(double)); // Free the excess. (Optional)
size_t m = j;
*b_ptr = b;
*m_ptr = m;
return 1;
}