go back to string

This commit is contained in:
Timerix22 2022-04-16 23:51:05 +03:00
parent d611287c1a
commit e1addc4004
10 changed files with 242 additions and 73 deletions

View File

@ -14,10 +14,11 @@ void StringBuilder_append_cptr(StringBuilder* b, char* s){
Autoarr_add(b,c);
}
void StringBuilder_append_string(StringBuilder* b, StringFragment s){
s.ptr+=s.offset;
while(s.length-->0)
void StringBuilder_append_string(StringBuilder* b, string s){
while(s.length>0){
Autoarr_add(b,*s.ptr++);
s.length--;
}
}
void StringBuilder_append_int64(StringBuilder* b, int64 a){
@ -35,7 +36,7 @@ void StringBuilder_append_int64(StringBuilder* b, int64 a){
buf[i++]='0'+a%10;
a/=10;
}
StringFragment rev=StringFragment_reverse((StringFragment){buf,0,i});
string rev=string_reverse((string){buf,i});
StringBuilder_append_string(b,rev);
free(rev.ptr);
}
@ -51,7 +52,8 @@ void StringBuilder_append_uint64(StringBuilder* b, uint64 a){
buf[i++]='0'+a%10;
a/=10;
}
StringFragment rev=StringFragment_reverse((StringFragment){buf,0,i});
string rev=string_reverse((string){buf,i});
printf("\e[95mrev:%s\n",string_cpToCptr(rev));
StringBuilder_append_string(b,rev);
free(rev.ptr);
}
@ -65,14 +67,11 @@ void StringBuilder_append_double(StringBuilder* b, double a){
StringBuilder_append_cptr(b,buf);
}
StringFragment StringBuilder_build(StringBuilder* b){
StringFragment str={
.offset=0,
.length=Autoarr_length(b)
};
str.ptr=malloc(str.length+1);
for(uint32 i=0; i<str.length; i++)
str.ptr[i]=Autoarr_get(b,i);
str.ptr[str.length]='\0';
char* StringBuilder_build(StringBuilder* b){
uint32 len=Autoarr_length(b);
char* str=malloc(len+1);
str[len]=0;
for(uint32 i=0;i<len;i++)
str[i]=Autoarr_get(b,i);
return str;
}

22
Autoarr/StringBuilder.h Normal file
View File

@ -0,0 +1,22 @@
#pragma once
#if __cplusplus
extern "C" {
#endif
#include "Autoarr.h"
typedef Autoarr(int8) StringBuilder;
StringBuilder StringBuilder_create(uint16 max_blocks_count, uint16 max_block_length);
void StringBuilder_append_char(StringBuilder* b, char c);
void StringBuilder_append_cptr(StringBuilder* b, char* s);
void StringBuilder_append_string(StringBuilder* b, string s);
void StringBuilder_append_int64(StringBuilder* b, int64 a);
void StringBuilder_append_uint64(StringBuilder* b, uint64 a);
void StringBuilder_append_double(StringBuilder* b, double a);
char* StringBuilder_build(StringBuilder* b);
#if __cplusplus
}
#endif

View File

@ -1,41 +1,23 @@
#include "DtsodV24.h"
#include "../StringFragment/StringBuilder.h"
#include "../Autoarr/StringBuilder.h"
#define ARR_BC 8
#define ARR_BL 16
#define STRB_BC 64
#define STRB_BL 1024
// special func for throwing error messages about wrong characters in deserializing text
Maybe ERROR_WRONGCHAR(const char c, char* text, char* text_first, const char* srcfile, int line, const char* funcname){
char errBuf[33];
errBuf[32]='\0';
char* errText=text-16;
if(errText<text_first) errText=text_first;
for(uint8 i=0; i<32; i++){
Maybe ERROR_WRONGCHAR(char c, char* text){
char errBuf[]="unexpected <c> at:\n \""
"00000000000000000000000000000000\"";
errBuf[12]=c;
for(uint8 i=0; i<32; i++)
// writes 16 chars before and 15 after the wrongchar
char _c=errText[i];
errBuf[i]=_c;
if(!_c) break;
}
char* errmsg=malloc(256);
IFWIN(
sprintf_s(errmsg,256, "unexpected <%c> at:\n"
" \"%s\"\n"
"\\___[%s:%d] %s()",
c,errBuf, srcfile,line,funcname),
sprintf(errmsg, "unexpected <%c> at:\n"
" \"%s\"\n"
" \\___[%s:%d] %s()",
c,errBuf, srcfile,line,funcname)
);
safethrow(cptr_copy(errmsg));
}
#define safethrow_wrongchar(C) return ERROR_WRONGCHAR(C, text, shared->sh_text_first, __FILE__,__LINE__,__func__)
errBuf[i+22]=*(text - 16 + i);
safethrow(cptr_copy(errBuf));
#define safethrow_wrongchar(C) return ERROR_WRONGCHAR(C, text)
typedef struct DeserializeSharedData{
const char* sh_text_first;
char* sh_text;
bool sh_partOfDollarList;
bool sh_readingList;
@ -56,7 +38,7 @@ Maybe __SkipComment(DeserializeSharedData* shared) {
Maybe __ReadName(DeserializeSharedData* shared){
char c;
StringFragment nameStr={text,0};
string nameStr={text,0};
text--;
while ((c=*++text)) switch (c){
case ' ': case '\t':
@ -82,7 +64,7 @@ Maybe __ReadName(DeserializeSharedData* shared){
if((*++text)!=';')
safethrow_wrongchar(c);
case ':':
return SUCCESS(UniPtr(CharPtr,StringFragment_extract(nameStr).ptr));
return SUCCESS(UniPtr(CharPtr,string_cpToCptr(nameStr)));
case '$':
if(nameStr.length!=0)
safethrow_wrongchar(c);
@ -117,9 +99,9 @@ Maybe __ReadString(DeserializeSharedData* shared){
StringBuilder_append_char(b,c);
}
else {
StringFragment str=StringBuilder_build(b);
char* str=StringBuilder_build(b);
Autoarr_clear(b);
return SUCCESS(UniPtr(CharPtr,str.ptr));
return SUCCESS(UniPtr(CharPtr,str));
}
}
else {
@ -144,6 +126,7 @@ Maybe __ReadList(DeserializeSharedData* shared){
};
#define ReadList() __ReadList(shared)
<<<<<<< HEAD
Maybe __ParseValue(DeserializeSharedData* shared, StringFragment str){
// printf("\e[94m<\e[96m%s\e[94m>\n",StringFragment_extract(str));
const StringFragment trueStr= {"true" ,0,4};
@ -152,10 +135,29 @@ Maybe __ParseValue(DeserializeSharedData* shared, StringFragment str){
// Bool
case 'e': {
if(StringFragment_compare(str,trueStr))
=======
Maybe __ParseValue(DeserializeSharedData* shared, string str){
//printf("\e[94m<\e[96m%s\e[94m>\n",string_cpToCptr(str));
const string nullStr={"null",4};
const string trueStr={"true",4};
const string falseStr={"false",5};
switch(*str.ptr){
case 'n':
if(string_compare(str,nullStr))
return SUCCESS(UniNull);
else safethrow_wrongchar(*str.ptr);
break;
case 't':
if(string_compare(str,trueStr))
>>>>>>> parent of 41f32f4 (string -> StringFragment, throw_wrongchar() fixed)
return SUCCESS(UniTrue);
else if(StringFragment_compare(str,falseStr))
else safethrow_wrongchar(*str.ptr);
break;
case 'f':
if(string_compare(str,falseStr))
return SUCCESS(UniFalse);
else safethrow_wrongchar(*str.ptr);
<<<<<<< HEAD
}
// Float64
case 'f': {
@ -191,15 +193,50 @@ Maybe __ParseValue(DeserializeSharedData* shared, StringFragment str){
// unknown type
default:
safethrow_wrongchar(str.ptr[str.length-1]);
=======
break;
default:
switch(str.ptr[str.length-1]){
case 'f': {
char* _c=string_cpToCptr(str);
Unitype rez=Uni(Float64,strtod(_c,NULL));
free(_c);
return SUCCESS(rez);
}
case 'u': {
uint64 lu=0;
char* _c=string_cpToCptr(str);
sscanf(_c,"%lu",&lu);
free(_c);
return SUCCESS(Uni(UInt64,lu));
}
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9': {
int64 li=0;
char* _c=string_cpToCptr(str);
if(sscanf(_c,"%li",&li)!=1){
char err[64];
IFWIN(
sprintf_s(err,64,"can't parse to int: <%s>",_c),
sprintf(err,"can't parse to int: <%s>",_c)
);
safethrow(err);
}
free(_c);
return SUCCESS(Uni(Int64,li));
}
default:
safethrow_wrongchar(str.ptr[str.length-1]);
}
>>>>>>> parent of 41f32f4 (string -> StringFragment, throw_wrongchar() fixed)
}
safethrow(ERR_ENDOFSTR);
};
#define ParseValue(str) __ParseValue(shared, str)
Maybe __ReadValue(DeserializeSharedData* shared){
char c;
StringFragment valueStr={text+1,0};
string valueStr={text+1,0};
Unitype value;
while ((c=*++text)) switch (c){
case ' ': case '\t':
@ -255,7 +292,6 @@ Maybe __ReadValue(DeserializeSharedData* shared){
Maybe __deserialize(char** _text, bool _calledRecursively) {
DeserializeSharedData _shared={
.sh_text_first=*_text,
.sh_text=*_text,
.sh_partOfDollarList=false,
.sh_readingList=false,

View File

@ -1,5 +1,5 @@
#include "DtsodV24.h"
#include "../StringFragment/StringBuilder.h"
#include "../Autoarr/StringBuilder.h"
// 65536 max length!
#define STRB_BC 64
@ -51,7 +51,8 @@ void __AppendValue(SerializeSharedData* shared, Unitype u){
StringBuilder_append_cptr(b, u.Bool ? "true" : "false");
break;
case Null:
throw("Null isn't supported in DtsodV24");
if(!u.VoidPtr) StringBuilder_append_cptr(b, "null");
else throw("Null-type pointer is not 0");
break;
case AutoarrUnitypePtr:
addc('[');
@ -96,7 +97,7 @@ void __serialize(StringBuilder* _b, uint8 _tabs, Hashtable* dtsod){
char* DtsodV24_serialize(Hashtable* dtsod){
StringBuilder sb=StringBuilder_create(STRB_BC,STRB_BL);
__serialize(&sb,0,dtsod);
StringFragment str=StringBuilder_build(&sb);
char* str=StringBuilder_build(&sb);
Autoarr_clear((&sb));
return str.ptr;
return str;
}

View File

@ -7,7 +7,7 @@ extern "C" {
#include "std.h"
#include "types.h"
#include "errors.h"
#include "cptr.h"
#include "mystr.h"
// executes codeblock and prints execution time
#ifdef CLOCK_REALTIME // non-standard high-precision clock

View File

@ -1,6 +1,6 @@
#include "std.h"
#include "errors.h"
#include "cptr.h"
#include "mystr.h"
char* errname(err_t err){
switch(err){

77
base/mystr.c Normal file
View File

@ -0,0 +1,77 @@
#include "base.h"
//returns length of string (including \0)
uint32 cptr_length(char* str){
uint32 len=0;
while(*(str++)) len++;
return ++len;
}
//allocates new char[] and copies src there
char* cptr_copy(char* src){
uint32 len=cptr_length(src);
char* dst=malloc(len*sizeof(char));
while(len-->0)
dst[len]=src[len];
return dst;
}
//compares two char buffers, NullPtr-friendly
bool cptr_compare(char* key0, char* key1){
if(!key0) return key1 ? false : true;
if(!key1) return false;
while(*key0&&*key1)
if(*key0++ != *key1++)
return false;
return true;
}
//multiplies char n times
char* char_multiply(char c, uint32 n){
char* rez=malloc(n+1);
rez[n]=0;
while(n-->0)
rez[n]=c;
return rez;
}
//copies str content to new char pointer value (adding '\0' at the end)
char* string_cpToCptr(string str){
if(str.length==0) return NULL;
char* cptr=malloc(str.length*sizeof(char)+1);
cptr[str.length]=0;
while(str.length-->0)
cptr[str.length]=str.ptr[str.length];
return cptr;
}
//copies cptr content (excluding '\0' at the end) to new string
string string_cpFromCharPtr(char* cptr){
if(!cptr) return stringNull;
string str;
str.length=cptr_length(cptr)-1;
str.ptr=malloc(str.length);
for(uint32 i=0;i<str.length;i++)
str.ptr[i]=cptr[i];
return str;
}
//compares two strings, NullPtr-friendly
bool string_compare(string str0, string str1){
if(str0.length!=str1.length) return false;
if(!str0.ptr) return str1.ptr ? false : true;
else if(!str1.ptr) return false;
while(str0.length-->0)
if(*str0.ptr++ != *str1.ptr++)
return false;
return true;
}
//creates new string which is reversed variant of <s>
string string_reverse(string s){
if(s.length==0) return s;
string r={malloc(s.length), s.length};
for(uint32 i=0; i<s.length; i++)
r.ptr[i]=s.ptr[s.length-i-1];
return r;
}

44
base/mystr.h Normal file
View File

@ -0,0 +1,44 @@
#pragma once
#if __cplusplus
extern "C" {
#endif
#include "types.h"
//returns length of string (including \0)
uint32 cptr_length(char* str);
//allocates new char[] and copies src there
char* cptr_copy(char* src);
//compares two char buffers, NullPtr-friendly
bool cptr_compare(char* key0, char* key1);
//multiplies char n times
char* char_multiply(char c, uint32 n);
//my fixed length string struct
//doesn't store '\0' at the end
typedef struct string{
char* ptr; //char pointer
uint32 length; //amount of chars in ptr value
} string;
static const string stringNull={NULL,0};
//copies str content to new char pointer value (adding '\0' at the end)
char* string_cpToCptr(string str);
//copies cptr content (excluding '\0' at the end) to new string
string string_cpFromCharPtr(char* cptr);
//compares two strings, NullPtr-friendly
bool string_compare(string str0, string str1);
//creates new string which is reversed variant of <s>
string string_reverse(string s);
#if __cplusplus
}
#endif

View File

@ -13,7 +13,7 @@ void test_all(){
int main(){
setlocale(LC_ALL, "en-US.Unicode");
printf("\e[92mdtsod parser in c language!\e[97m\n");
optime("test_all",1,test_all());
optime("test_all",1,{test_all();});
printf("\e[0m\n");
return 0;
}

View File

@ -1,26 +1,16 @@
#include "tests.h"
#include "../StringFragment/StringFragment.h"
#include "../base/mystr.h"
void test_string(){
optime(__func__,1,({
printf("\e[96m-------------[test_string]-------------\n");
char c[]="0123456789abcdef";
StringFragment s={.ptr=cptr_copy(c),.offset=0,.length=cptr_length(c)};
printf("\e[92m\"%s\" \e[94m-> StringFragment\n",c);
if(s.length!=16) throw("StringFragment created with incorrect length");
StringFragment extr=StringFragment_extract(s);
printf("\e[94mStringFragment_extract() -> \e[92m\"%s\"\n",extr.ptr);
if(extr.length!=16) throw("StringFragment extracted with incorrect length");
free(extr.ptr);
s.offset+=2; s.length-=4;
printf("\e[94mStringFragment offset+=2 length-=4\n");
extr=StringFragment_extract(s);
printf("\e[94mStringFragment_extract() -> \e[92m\"%s\"\n",extr.ptr);
if(extr.length!=12) throw("StringFragment extracted with incorrect length");
string s=string_cpFromCharPtr(c);
printf("\e[92m\"%s\" \e[94m-> string_cpFromCharPtr()\n",c);
if(s.length!=16) throw("string created with incorrect length");
char* p=string_cpToCptr(s);
printf("\e[94mstring_cpToCptr() -> \e[92m\"%s\"\n",p);
free(p);
free(s.ptr);
free(extr.ptr);
}));
}