diff --git a/BuildDataBase.c b/BuildDataBase.c index 8546139707f390d657027b80396caf512f6ccec9..a81702bbe3d0a2084fdfbdd51918302aa0d310a1 100644 --- a/BuildDataBase.c +++ b/BuildDataBase.c @@ -20,21 +20,43 @@ // Import headers. +//#include <string.h> +//#include <stdlib.h> +//#include <ctype.h> +#include <fcntl.h> #include <stdio.h> -#include <string.h> -#include <stdlib.h> -#include <ctype.h> +#include <sys/stat.h> +#include <sys/types.h> +#include <unistd.h> #include "apue.h" // Define Vars. -#define BUFFERSIZE 4096; +#define BUFFER_SIZE 4096 +#define ARRAY_SIZE 500 // Variables. +typedef struct { + char* artist; + char* song_name; + char* album_name; + float* duration; + int* year; + double* hotttnesss; +} songs_struct; // Songs struct. + +int songs_array_max = ARRAY_SIZE; // Saves current size of songs array. +int current_song = 0; // Current song value to save. +songs_struct** songs_array; // The array which holds all song pointers. // Method Declaration. +int open_file(); // Initially opens file to read. +void read_file(); // Reads in chunk of file. +void read_line(); // Separates file chunk into lines. +void tokenize_line(); // Separates lines into fields. +void populate_array(); // Populates array with fields. /** @@ -42,5 +64,153 @@ * Initializes and runs program. */ int main(int argc, char* argv[]) { + int file_descriptor = open_file(); + read_file(file_descriptor); +} + + +/** + * Opens file. + */ +int open_file() { + int file_descriptor = open("Data/SongCSV_Small.csv", O_RDONLY); + if (file_descriptor < 0) { + err_sys("Failed to open file."); + } + return file_descriptor; +} + + +/** + * Read next chunk of file. + * + * Return: Next chunk of file read. + */ +void read_file(int file_descriptor) { + char *read_buffer; + char *temp_buffer; + int index; + int offset_amount; + size_t read_size; + + read_buffer = calloc(BUFFER_SIZE, sizeof(char)); + temp_buffer = calloc(BUFFER_SIZE, sizeof(char)); + + off_t read_value = read(file_descriptor, read_buffer, BUFFER_SIZE); + if (read_value < 0) { + err_sys("Failed to read line."); + } + + // Start from end of buffer. Read backwards until first null terminator + // is found. + index = BUFFER_SIZE - 1; + offset_amount = 0; + *temp_buffer = *read_buffer; + printf("Looping through buffer...\n"); + while (index > 0) { + //printf("%s", read_buffer); + //printf("%c", temp_buffer[index]); + if (temp_buffer[index] == '\n') { + // Found first null terminator. Save location and exit loop. + offset_amount = index; + index = 0; + } + index--; + } + + // Set "Read Size" for lseek to travel to last null terminator. + read_size = BUFFER_SIZE - offset_amount; + off_t offset_size = lseek(file_descriptor, read_size, SEEK_CUR); + if (offset_size < 0) { + err_sys("Failed to update pointer on read in."); + } + + printf("Buffer: %d, Offset: %d, ReadSize: %ld\n\n", BUFFER_SIZE, offset_amount, read_size); + //write(1, read_buffer, BUFFER_SIZE); + //write(1, read_buffer, read_size); + printf("\n\n"); + read_line(read_buffer, read_size); +} + + +/** + * Separates individual lines out of file chunk. + */ +void read_line(char *read_buffer, size_t read_size) { + int chunk_index = 0; + int line_index = 0; + char *line_buffer; + + line_buffer = calloc(BUFFER_SIZE, sizeof(char)); + + printf("Looping through for individual lines...\n"); + // Loop through entire chunk. + while ((chunk_index < read_size) && (strcmp(&read_buffer[chunk_index], "\0") != 0)) { + // Loop through individual line and copy values. + if (read_buffer[chunk_index] == '\r') { + // Newline so current line is done being read. + line_buffer[line_index] = '\0'; + tokenize_line(line_buffer); + line_index = 0; + chunk_index++; + + // Free and reallocate memory for next line. + free(line_buffer); + line_buffer = calloc(BUFFER_SIZE, sizeof(char)); + } else { + // Newline not found so save value and keep reading. + line_buffer[line_index] = read_buffer[chunk_index]; + line_index++; + chunk_index++; + } + } + printf("\n"); +} + + +/** + * Separates individual fields out of line. + */ +void tokenize_line(char *line_buffer) { + int line_index = 0; + int field_index = 0; + int field_number = 0; + char* field_buffer; + + printf("\n\nTokenizing line...\n"); + field_buffer = calloc(BUFFER_SIZE, sizeof(char)); + + while (strcmp(&line_buffer[line_index], "\0") != 0) { + // Check for comma to denote next field. + if (line_buffer[line_index] == ',') { + // Found comma so end of field. Handle appropriately. + field_index = 0; + line_index++; + + if (strcmp(field_buffer, "") != 0) { + printf("%s\n", field_buffer); + populate_array(field_number, field_buffer); + field_number++; + } + + free(field_buffer); + field_buffer = calloc(BUFFER_SIZE, sizeof(char)); + } else { + // No comma found. + field_buffer[field_index] = line_buffer[line_index]; + //printf("%c", line_buffer[line_index]); + //printf("%c", field_buffer[field_index]); + field_index++; + line_index++; + } + } + current_song++; +} + + +/** + * Takes provided field value and associates with song in struct. + */ +void populate_array(int field_number, char *field_value) { }