add json printing and parsing (of strings)
This commit is contained in:
parent
563b1b0c5a
commit
a13c6ecb3a
6 changed files with 277 additions and 81 deletions
150
json.c
Normal file
150
json.c
Normal file
|
@ -0,0 +1,150 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "json.h"
|
||||
#include "sortedmap.h"
|
||||
#include "arraylist.h"
|
||||
|
||||
/* TODO */
|
||||
Json * parse_map(FILE *stream) { return NULL; /* TODO */ }
|
||||
Json * parse_list(FILE *stream) { return NULL; /* TODO */ }
|
||||
|
||||
Json * parse_string(FILE *stream) {
|
||||
int i = 0, cap = 10;
|
||||
char * buffer = calloc(cap, sizeof(char));
|
||||
char c;
|
||||
int escaped = 0;
|
||||
Json * json;
|
||||
while ((c = getc(stream)) != EOF) {
|
||||
printf("char: %c, buffer: %s, i: %d\n", c, buffer, i);
|
||||
switch (c) {
|
||||
case '\\':
|
||||
escaped = 1;
|
||||
break;
|
||||
case '"':
|
||||
if (!escaped) {
|
||||
json = malloc(sizeof(Json));
|
||||
json->type = STRING;
|
||||
json->value.string = calloc(i + 1, sizeof(char));
|
||||
memcpy(json->value.string, buffer, i);
|
||||
free(buffer);
|
||||
return json;
|
||||
}
|
||||
default:
|
||||
if (i == cap) {
|
||||
cap *= 2;
|
||||
buffer = realloc(buffer, cap * sizeof(char));
|
||||
}
|
||||
buffer[i++] = c;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
Json * parse_true(FILE *stream) { return NULL; /* TODO */ }
|
||||
Json * parse_false(FILE *stream) { return NULL; /* TODO */ }
|
||||
Json * parse_number(FILE *stream, char first) { return NULL; /* TODO */ }
|
||||
|
||||
Json * json_parse(FILE *stream) {
|
||||
char c;
|
||||
Json * json = NULL;
|
||||
while ((c = getc(stream)) != EOF) {
|
||||
switch (c) {
|
||||
case '{':
|
||||
return parse_map(stream);
|
||||
case '[':
|
||||
return parse_list(stream);
|
||||
case '"':
|
||||
return parse_string(stream);
|
||||
case 't':
|
||||
return parse_true(stream);
|
||||
case 'f':
|
||||
return parse_false(stream);
|
||||
case '0':
|
||||
case '1':
|
||||
case '2':
|
||||
case '3':
|
||||
case '4':
|
||||
case '5':
|
||||
case '6':
|
||||
case '7':
|
||||
case '8':
|
||||
case '9':
|
||||
return parse_number(stream, c);
|
||||
case ' ':
|
||||
case '\n':
|
||||
case '\t':
|
||||
break; /* whitespace */
|
||||
default:
|
||||
fprintf(stderr, "encountered char: '%c'", c);
|
||||
}
|
||||
}
|
||||
return json;
|
||||
}
|
||||
|
||||
struct printacc {
|
||||
FILE *stream;
|
||||
int index;
|
||||
};
|
||||
|
||||
void * json_print_map(void * voidacc, char *key, void *value) {
|
||||
struct printacc *acc = (struct printacc *) voidacc;
|
||||
|
||||
return acc;
|
||||
}
|
||||
|
||||
void json_print(Json *this, FILE *stream) {
|
||||
int i;
|
||||
struct printacc acc = { NULL, 0 };
|
||||
switch (this->type) {
|
||||
case BOOLEAN:
|
||||
fprintf(stream, this->value.boolean == 0 ? "false" : "true");
|
||||
break;
|
||||
case STRING:
|
||||
fprintf(stream, "\"%s\"", this->value.string);
|
||||
break;
|
||||
case NUMBER:
|
||||
fprintf(stream, "%f", this->value.number);
|
||||
break;
|
||||
case LIST:
|
||||
fprintf(stream, "[");
|
||||
if (this->value.list->size > 0) {
|
||||
json_print((Json *) get_list(this->value.list, 0), stream);
|
||||
for(i = 1; i < this->value.list->size; i++) {
|
||||
fprintf(stream, ", ");
|
||||
json_print((Json *) get_list(this->value.list, i), stream);
|
||||
}
|
||||
}
|
||||
fprintf(stream, "]");
|
||||
break;
|
||||
case MAP:
|
||||
fprintf(stream, "{");
|
||||
acc.stream = stream;
|
||||
fold_map((void *) &acc, this->value.map, json_print_map);
|
||||
fprintf(stream, "}");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void json_free(Json *this) {
|
||||
switch (this->type) {
|
||||
case BOOLEAN:
|
||||
/* TODO */
|
||||
break;
|
||||
case STRING:
|
||||
/* TODO */
|
||||
free(this->value.string);
|
||||
break;
|
||||
case NUMBER:
|
||||
/* TODO */
|
||||
break;
|
||||
case LIST:
|
||||
/* TODO */
|
||||
break;
|
||||
case MAP:
|
||||
/* TODO */
|
||||
break;
|
||||
}
|
||||
free(this);
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue