Chris M. Thomasson said:
Peter Jansson said:
Dear news group,
I have created a small programming challenge for those of you who are
interested in challenging your Standard C++ programming skills. The
challenge is about counting character frequency in large texts,
perhaps useful for spam filtering or classical crypto analysis. You
can read more about it here:
http://blog.p-jansson.com/2009/06/programming-challenge-letter-frequency.html
Well, try this one out too:
_______________________________________________________________________________
#include <stdio.h>
#include <limits.h>
#define BUFFER 65536U
int main(int argc, char** argv) {
size_t i;
unsigned long total = 0;
unsigned long counts[UCHAR_MAX + 1] = { 0 };
FILE* file = fopen(argv[1], "rb");
if (file) {
size_t size;
static unsigned char buf[BUFFER];
while ((size = fread(buf, 1, BUFFER, file))) {
while (size) {
--size;
++counts[buf[size]];
}
if (size < BUFFER) {
if (feof(file) || ferror(file)) break;
}
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
lol. How is the that last if block ever going to executed!
[...]
_______________________________________________________________________________
It just might beat my previous submission by a little bit...
This one actually tries to check for errors:
_______________________________________________________________________________
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <limits.h>
#if ! defined (FILE_MODE)
# define FILE_MODE "rb"
#endif
typedef char sassert[
'Z' - 'A' == 25 &&
'z' - 'a' == 25 ? 1 : -1
];
#define BUFFER 65536U
#define GET_COUNT(mp_self, mp_index) ( \
(mp_self)[(mp_index) + 'a'] + \
(mp_self)[(mp_index) + 'A'] \
)
int main(int argc, char** argv) {
if (argc > 1) {
size_t i;
unsigned long total = 0;
unsigned long counts[UCHAR_MAX + 1] = { 0 };
FILE* file = fopen(argv[1], FILE_MODE);
if (file) {
size_t size;
int status = EXIT_SUCCESS;
static unsigned char buf[BUFFER];
while ((size = fread(buf, 1, BUFFER, file))) {
size_t tmpsize = size;
while (tmpsize) {
++counts[buf[--tmpsize]];
}
if (size < BUFFER) break;
}
if (ferror(file)) status = EXIT_FAILURE;
if (fclose(file)) status = EXIT_FAILURE;
if (status == EXIT_SUCCESS) {
for (i = 0; i < 26; ++i) {
total += GET_COUNT(counts, i);
}
for (i = 0; i < 26; ++i) {
printf("%c %%%.3f\n", (char)(i + 'a'),
(total) ? ((double)GET_COUNT(counts, i) / total) * 100.0 : 0.0);
}
return EXIT_SUCCESS;
}
}
}
fprintf(stderr, "file error...");
assert(0);
return EXIT_FAILURE;
}
_______________________________________________________________________________
GRRRR!