Skip to content

Instantly share code, notes, and snippets.

@wilfreddv
Last active September 8, 2021 15:21
Show Gist options
  • Save wilfreddv/1d352313e3d93d2d8d637ae0f5e826f2 to your computer and use it in GitHub Desktop.
Save wilfreddv/1d352313e3d93d2d8d637ae0f5e826f2 to your computer and use it in GitHub Desktop.
Print a histogram
#include <stdio.h>
#include <string.h>
#include <limits.h>
static inline unsigned _max(unsigned values[], unsigned length) {
unsigned max = 0;
for(unsigned i = 0; i < length; i++) max = max > values[i] ? max : values[i];
return max;
}
void histogram(char* keys[], unsigned values[], unsigned length, unsigned max_height) {
unsigned max = _max(values, length);
max_height = max_height > max ? max : max_height;
char max_nlenbuf[15];
// Needed for padding of the y-axis
sprintf(max_nlenbuf, "%d", UINT_MAX);
short max_nlen = strlen(max_nlenbuf);
unsigned granularity = max / max_height;
unsigned llens[length];
for(unsigned i = 0; i < length; i++) llens[i] = strlen(keys[i]);
unsigned pad = _max(llens, length) + 1;
pad += pad % 2;
for(unsigned step = max_height; step > 0; step--) {
printf("%-*u:", max_nlen, (step*granularity));
for(unsigned i = 0; i < length; i++) {
char* bar = " ";
if( values[i] >= step*granularity )
bar = "█";
for(unsigned _=0; _<strlen(keys[i])/2; _++) putchar(' ');
fputs(bar, stdout);
#ifdef WIDEPRINT
for(unsigned _=0; _<pad-1-strlen(keys[i])/2; _++) putchar(' ');
#else
for(unsigned _=0; _<strlen(keys[i])/2+1+(strlen(keys[i])%2); _++) putchar(' ');
#endif
}
printf("\n");
}
printf("%-*s", max_nlen+1, "");
for(unsigned i = 0; i < length; i++) {
#ifdef WIDEPRINT
printf("%-*s", pad, keys[i]);
#else
printf("%-*s", (int)strlen(keys[i])+2, keys[i]);
#endif
}
printf("\n");
}
#ifndef _H_HISTOGRAM
#define _H_HISTOGRAM
void histogram(char* keys[], unsigned values[], unsigned length, unsigned max_height);
#endif // _H_HISTOGRAM
#include "histogram.h"
int main() {
char* keys[] = {"foo", "bar", "baz", "quux", "biz", "booze"};
unsigned values[] = {15, 3, 20, 32, 9, 16 };
histogram(keys, values, sizeof(keys)/sizeof(keys[0]), 10);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment