I have a problem where I need to read in multiple arrays from a .txt file and output the maximum sum subarray. Here is the text file:
[1, 4, -9, 8, 1, 3, 3, 1, -
Divide and conquer. Break task into pieces. Putting each piece into a separate function helps.
unable to figure out how to read the integers in and place them in separate arrays
Only 2 int
arrays needed: The current array of int
read and the best one. Use read_ints()
to read one line. Various tests were applied to insure data was as expected. A classic approach is to read a line into a buffer (might need 100*40 char
for a worst case) and then process it. The below reads pieces of a line, look for the start-of-Frame '['
and end-of-frame ']'
to insure data integrity.
#include <ctype.h>
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define StartOfFrame '['
#define Separator ','
#define EndOfFrame ']'
#define INT_COUNT_MAX 100
// Return number of `int` read
// or 0 on syntax error
// or EOF
int read_ints(int *dest, int size, FILE *inf) {
int ch;
char delimiter = 0;
ch = fgetc(inf);
if (ch == EOF) return EOF;
if (ch != StartOfFrame) return 0; // unexpected text
int i;
for (i = 0; i < size; i++) {
if (fscanf(inf, "%d%c", &dest[i], &delimiter) != 2) return 0;
if (delimiter == EndOfFrame) break;
if (delimiter != Separator) return 0;
}
do {
ch = fgetc(inf);
if (ch == '\n' || ch == EOF) return i;
} while (isspace(ch));
return 0; // unexpected text
}
OP's offered double maxSubArray(double * Array1);
, but that lacks a length of valid int
. Of course that array could be pre-filled with 0.
In writing a complete solution, the various error checking helped in quickly identifying problems.
The below read_lines()
wraps the repeated calls of read_ints()
and processes the results.
OP Ignore the rest should you not want to see the complete solution.
int read_lines(FILE *inf) {
int best[INT_COUNT_MAX];
unsigned best_line = 0;
int best_count = 0;
long long best_sum = LLONG_MIN;
int a[INT_COUNT_MAX];
unsigned line_count = 0;
int count;
while ((count = read_ints(a, INT_COUNT_MAX, inf)) >= 0) {
line_count++;
if (count == 0) {
fprintf(stderr, "Trouble reading line %u\n", line_count);
return 1;
}
long long sum = 0;
for (int i = 0; i < count; i++) {
sum += a[i];
}
if (sum > best_sum) {
best_sum = sum;
best_count = count;
best_line =line_count;
memcpy(best, a, sizeof best[0] * count);
}
}
printf("Greatest sum:%lld on line:%u\n", best_sum, best_line);
fputc(StartOfFrame, stdout);
for (int i = 0; i < best_count; i++) {
if (i > 0) printf("%c", Separator);
printf("%d", best[i]);
}
fputc(EndOfFrame, stdout);
return 0;
}
int main(void) {
const char *filename = "MSS_TestProblems.txt";
FILE *myFile;
myFile = fopen(filename, "r");
if (!myFile) {
fprintf(stderr, "Unable to open file \"%s\"\n", filename);
return 1;
}
read_lines(myFile);
fclose(myFile);
return 0;
}
--
Greatest sum:81 on line:6
[12,99,99,-99,-27,0,0,0,-3]
Read in the file with fread
calls into a buffer. Explode buffer per line (\n) / array. (Count how many arrays do you need and prepare.) Explode lines per numbers - separator: comma and space. (Count length of array and allocate.) Numbers would contain sign and digits. Assuming digits are contiguous in range '0'..'9', '0'+digit gives the value of the digit. Value of the number can be calculated from sign, digit values and their order.