123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465 |
- #include "__ofunc.h"
- ResultType tuple_list_newCore(OFFICAL_FUNCTIONSIG, enum ListType type){
- LinkValue *value = NULL;
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=true},
- {.must=-1}};
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- value = make_new(inter, belong, ap[0].value);
- value->value->type = list;
- value->value->data.list.type = type;
- value->value->data.list.list = NULL;
- value->value->data.list.size = 0;
- for (Argument *at = ap[1].arg; at != NULL && at->type == value_arg; at = at->next) {
- value->value->data.list.size++;
- value->value->data.list.list = memRealloc(value->value->data.list.list, value->value->data.list.size * sizeof(LinkValue *));
- value->value->data.list.list[value->value->data.list.size - 1] = at->data.value;
- }
- switch (init_new(value, NULL, "list.new", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong))) {
- case 1:
- freeResult(result);
- setResultOperation(result, value);
- break;
- default:
- break;
- } // TODO-szh 提取成函数
- return result->type;
- }
- ResultType tuple_new(OFFICAL_FUNCTIONSIG) {
- return tuple_list_newCore(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), value_tuple);
- }
- ResultType list_new(OFFICAL_FUNCTIONSIG) {
- return tuple_list_newCore(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), value_list);
- }
- ResultType list_slice(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum first;
- vnum second;
- vnum stride;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list) {
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- first = 0;
- second = size;
- stride = 1;
- for (vnum *list[]={&first, &second, &stride}, i=0; i < 3; i++) {
- if (ap[i + 1].value != NULL && ap[i + 1].value->value->type == number)
- *(list[i]) = ap[i + 1].value->value->data.num.num;
- else if (ap[i + 1].value != NULL && ap[i + 1].value->value->type != none) {
- setResultError(E_TypeException, ONLY_ACC(first/second/stride, number or none), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- }
- if (!checkSlice(&first, &second, &stride, size, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
- return result->type;
- {
- Argument *new_list = NULL;
- for (vnum i = stride > 0 ? first : second; stride > 0 ? (i < second) : (i > first); i += stride) {
- LinkValue *element = ap[0].value->value->data.list.list[i];
- new_list = connectValueArgument(element, new_list);
- }
- makeListValue(new_list, 0, "list.slice", value_list, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- freeArgument(new_list, true);
- }
- return result->type;
- }
- ResultType list_slice_assignment(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum first;
- vnum second;
- vnum stride;
- LinkValue *iter_obj = NULL;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list) {
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "sys", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- getIter(ap[1].value, 1, 0, "list", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- iter_obj = result->value;
- result->value = NULL;
- freeResult(result);
- first = 0;
- second = size;
- stride = 1;
- for (vnum *list[]={&first, &second, &stride}, i=0; i < 3; i++) {
- if (ap[i + 2].value != NULL && ap[i + 2].value->value->type == number)
- *(list[i]) = ap[i + 2].value->value->data.num.num;
- else if (ap[i + 2].value != NULL && ap[i + 2].value->value->type != none) {
- setResultError(E_TypeException, ONLY_ACC(first/second/stride, num or null), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- goto return_;
- }
- }
- if (!checkSlice(&first, &second, &stride, size, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
- goto return_;
- {
- for (vnum i = stride > 0 ? first : second; stride > 0 ? (i < second) : (i > first); i += stride) {
- freeResult(result);
- getIter(iter_obj, 0, 0, "list", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (is_iterStop(result->value, inter)){
- setResultError(E_TypeException, "Iter Object Too Short", 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- goto return_;
- }
- else if (!CHECK_RESULT(result))
- goto return_;
- ap[0].value->value->data.list.list[i] = result->value;
- }
- freeResult(result);
- getIter(iter_obj, 0, 0, "list", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (CHECK_RESULT(result)) {
- setResultError(E_TypeException, "Iter Object Too Long", 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- goto return_;
- } else if (!is_iterStop(result->value, inter))
- goto return_;
- }
- setResult(result, inter, belong);
- return_:
- gc_freeTmpLink(&iter_obj->gc_status);
- return result->type;
- }
- ResultType list_slice_del(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.type=only_value, .must=0, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum first;
- vnum second;
- vnum stride;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list) {
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- first = 0;
- second = size;
- stride = 1;
- for (vnum *list[]={&first, &second, &stride}, i=0; i < 3; i++) {
- if (ap[i + 1].value != NULL && ap[i + 1].value->value->type == number)
- *(list[i]) = ap[i + 1].value->value->data.num.num;
- else if (ap[i + 1].value != NULL && ap[i + 1].value->value->type != none) {
- setResultError(E_TypeException, ONLY_ACC(first/second/stride, num or null), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- }
- if (!checkSlice(&first, &second, &stride, size, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
- return result->type;
- {
- LinkValue **new = NULL;
- vnum new_size = size;
- for (vnum i = stride > 0 ? first : second; stride > 0 ? (i < second) : (i > first); i += stride) {
- ap[0].value->value->data.list.list[i] = NULL;
- new_size --;
- }
- new = memCalloc(new_size, sizeof(LinkValue *));
- for (vnum i = 0, c = 0; i < size; i++) {
- if (ap[0].value->value->data.list.list[i] != NULL){
- new[c] = ap[0].value->value->data.list.list[i];
- c++;
- }
- }
- memFree(ap[0].value->value->data.list.list);
- ap[0].value->value->data.list.list = new;
- ap[0].value->value->data.list.size = new_size;
- }
- return result->type;
- }
- ResultType list_down_assignment(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum index;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list){
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- if (ap[2].value->value->type != number){
- setResultError(E_TypeException, ONLY_ACC(list index, number), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- index = ap[2].value->value->data.num.num;
- if (index < 0)
- index = size + index;
- if (index >= size){
- setResultError(E_IndexException, "Index too max", 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- } else if (index < 0){
- setResultError(E_IndexException, "Index less than 0", 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- ap[0].value->value->data.list.list[index] = ap[1].value;
- setResultOperationBase(result, ap[1].value);
- return result->type;
- }
- ResultType list_down_del(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum index;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list){
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- if (ap[1].value->value->type != number){
- setResultError(E_TypeException, ONLY_ACC(list index, number), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- index = ap[1].value->value->data.num.num;
- if (!checkIndex(&index, &size, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
- return result->type;
- {
- LinkValue **new = NULL;
- new = memCalloc(size - 1, sizeof(LinkValue *));
- memcpy(new, ap[0].value->value->data.list.list, sizeof(LinkValue *) * index);
- memcpy(new + index, ap[0].value->value->data.list.list + index + 1, sizeof(LinkValue *) * (size - index - 1));
- memFree(ap[0].value->value->data.list.list);
- ap[0].value->value->data.list.list = new;
- ap[0].value->value->data.list.size --;
- }
- setResult(result, inter, belong);
- return result->type;
- }
- ResultType list_down(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.type=only_value, .must=1, .long_arg=false},
- {.must=-1}};
- vnum size;
- vnum index;
- LinkValue *element = NULL;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list){
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- if (ap[1].value->value->type != number){
- setResultError(E_TypeException, ONLY_ACC(list index, number), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- size = ap[0].value->value->data.list.size;
- index = ap[1].value->value->data.num.num;
- if (!checkIndex(&index, &size, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong)))
- return result->type;
- element = ap[0].value->value->data.list.list[index];
- setResultOperationBase(result, copyLinkValue(element, inter));
- return result->type;
- }
- ResultType list_iter(OFFICAL_FUNCTIONSIG){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.must=-1}};
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- if (ap[0].value->value->type != list){
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "list", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- {
- Argument *list_iter_arg = makeValueArgument(ap[0].value);
- callBackCore(inter->data.list_iter, list_iter_arg, 0, "list", 0,
- CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- freeArgument(list_iter_arg, true);
- }
- return result->type;
- }
- ResultType listRepoStrCore(OFFICAL_FUNCTIONSIG, bool is_repo){
- ArgumentParser ap[] = {{.type=only_value, .must=1, .long_arg=false},
- {.must=-1}};
- char *repo = NULL;
- Value *value = NULL;
- LinkValue *again = NULL;
- enum ListType lt;
- setResultCore(result);
- parserArgumentUnion(ap, arg, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- freeResult(result);
- value = ap[0].value->value;
- if (value->type != list){
- setResultError(E_TypeException, INSTANCE_ERROR(list), 0, "sys", true, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return error_return;
- }
- lt = value->data.list.type;
- again = findAttributes(is_repo ? "repo_again" : "str_again", false, ap[0].value, inter);
- if (again != NULL){
- bool again_ = checkBool(again, 0, "sys", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- return result->type;
- if (again_) {
- makeStringValue(lt == value_list ? "[...]" : "(...)", 0, "list.repo", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return result->type;
- }
- }
- setBoolAttrible(true, is_repo ? "repo_again" : "str_again", 0, "list.repo", ap[0].value, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (lt == value_list)
- repo = memStrcpy("[");
- else
- repo = memStrcpy("(");
- for (int i=0;i < value->data.list.size;i++){
- char *tmp;
- freeResult(result);
- if (i > 0)
- repo = memStrcat(repo, ", ", true, false);
- tmp = getRepoStr(value->data.list.list[i], is_repo, 0, "sys", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- if (!CHECK_RESULT(result))
- goto return_;
- repo = memStrcat(repo, tmp, true, false);
- }
- if (lt == value_list)
- repo = memStrcat(repo, "]", true, false);
- else
- repo = memStrcat(repo, ")", true, false);
- freeResult(result);
- makeStringValue(repo, 0, "list.repo", CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, result, belong));
- return_:
- {
- Result tmp;
- setResultCore(&tmp);
- setBoolAttrible(false, is_repo ? "repo_again" : "str_again", 0, "list.repo", ap[0].value, CALL_INTER_FUNCTIONSIG_NOT_ST(var_list, &tmp, belong));
- if (!RUN_TYPE(tmp.type)) {
- freeResult(result);
- *result = tmp;
- } else
- freeResult(&tmp);
- }
- memFree(repo);
- return result->type;
- }
- ResultType list_repo(OFFICAL_FUNCTIONSIG){
- return listRepoStrCore(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), true);
- }
- ResultType list_str(OFFICAL_FUNCTIONSIG){
- return listRepoStrCore(CALL_OFFICAL_FUNCTION(arg, var_list, result, belong), false);
- }
- void registeredList(REGISTERED_FUNCTIONSIG){
- {
- LinkValue *object = inter->data.tuple;
- NameFunc tmp[] = {{inter->data.object_new, tuple_new, class_free_},
- {inter->data.object_down, list_down, object_free_},
- {inter->data.object_slice, list_slice, object_free_},
- {inter->data.object_iter, list_iter, object_free_},
- {inter->data.object_repo, list_repo, object_free_},
- {inter->data.object_str, list_str, object_free_},
- {inter->data.object_down_del, list_down_del, object_free_},
- {inter->data.object_slice_del, list_slice_del, object_free_},
- {NULL, NULL}};
- gc_addTmpLink(&object->gc_status);
- addBaseClassVar("tuple", object, belong, inter);
- iterBaseClassFunc(tmp, object, CALL_INTER_FUNCTIONSIG_CORE(inter->var_list));
- gc_freeTmpLink(&object->gc_status);
- }
- {
- LinkValue *object = inter->data.list;
- NameFunc tmp[] = {{inter->data.object_new, list_new, class_free_},
- {inter->data.object_down_assignment, list_down_assignment, object_free_},
- {inter->data.object_slice_assignment, list_slice_assignment, object_free_},
- {NULL, NULL}};
- gc_addTmpLink(&object->gc_status);
- addBaseClassVar("list", object, belong, inter);
- iterBaseClassFunc(tmp, object, CALL_INTER_FUNCTIONSIG_CORE(inter->var_list));
- gc_freeTmpLink(&object->gc_status);
- }
- }
- void makeBaseList(Inter *inter){
- LinkValue *tuple = makeBaseChildClass4(inter->data.vobject, inter);
- LinkValue *list = makeBaseChildClass4(tuple, inter);
- gc_addStatementLink(&tuple->gc_status);
- gc_addStatementLink(&list->gc_status);
- inter->data.tuple = tuple;
- inter->data.list = list;
- }
|