Thanks for the advice. I changed the code in the main and tested the while(fscanf). i write the unsorted data to the new file webstats.sorted. I searched in text and the web for quicksort data stored in files. I found this particular quicksort code from a text. how can i sort the data by the ip address field if the ip has the '.'. Is it the same way as I did it with the ':' delimeter in the fscanf in main?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define NUM_ELEMENTS 12123 /* really need to use a counter */
struct IP
{
char ip[30];
char requests[20];
char bytes[30];
}stats;
int main(int argc, char *argv[])
{
FILE *fp, *out;
int index;
char temp[51];
char c;
if((fp=fopen(argv[1],"r"))==NULL)
{
printf("%d Error: cannot open file\n", argc);
exit(1);
}
if((out=fopen("webstats.sorted","w"))==NULL)
{
printf("Error:cannot open file for write.\n");
exit(1);
}
for(index = 0; index < 13; index++)
{
fgets(temp, sizeof(temp), fp);
} /* ignore the comments */
printf("Writing unsorted data to disk.\n");
/* c is the ':' delimeter */
while(fscanf(fp, "%s %c %s %c %s", stats.ip, &c, stats.requests,
&c, stats.bytes) != EOF)
{
/* write to the file out */
fprintf(out, "%s %c %s %c %s\n", stats.ip, c, stats.requests,
c, stats.bytes);
}
printf("%s %c %s %c %s\n", stats.ip, stats.requests,
stats.bytes); /* test - whats in the structure */
printf("Sorting disk file.\n");
quick_disk(out, NUM_ELEMENTS);
fclose(fp); /* close the file */
fclose(out);
printf("List sorted.\n");
return(0);
}
void quick_disk(FILE *fp, int count)
{
qs_disk(fp, 0, count -1);
}
void qs_disk(FILE *fp, int left, int right)
{
long int i, j;
char x[100];
i = left; j = right;
strcpy(x, getIP(fp, (long)(i+j)/2));
do
{
while((strcmp(getIP(fp,i),x) < 0) && (i < right)) i++;
while((strcmp(getIP(fp,j),x) > 0) && (j > left)) j--;
if(i <= j)
{
swap_all_fields(fp, i, j);
i++; j--;
}
} while(i <= j);
if(left < j) qs_disk(fp, left, (int) j);
if(i < right) qs_disk(fp, (int) i, right);
}
void swap_all_fields(FILE *fp, long i, long j)
{
char a[sizeof(stats)], b[sizeof(stats)];
fseek(fp, sizeof(stats)*i, SEEK_SET);
fread(a, sizeof(stats), 1, fp);
fseek(fp, sizeof(stats)*j, SEEK_SET);
fread(b, sizeof(stats), 1, fp);
fseek(fp, sizeof(stats)*j, SEEK_SET);
fwrite(a, sizeof(stats), 1, fp);
fseek(fp, sizeof(stats)*i, SEEK_SET);
fwrite(b, sizeof(stats), 1, fp);
}
char *getIP(FILE *fp, long rec)
{
struct IP *ip_address;
ip_address = &stats;
fseek(fp, rec*sizeof(stats), SEEK_SET);
fread(ip_address, sizeof(stats), 1, fp);
return stats.ip;
}
gbilios
|