REF: adding ref function for arrays deref.
parent
d9e06eeabd
commit
a08f722598
|
@ -1,13 +1,13 @@
|
||||||
(assert= 8 ([2 6 2 8 9] 3))
|
(assert= 8 (ref [2 6 2 8 9] 3))
|
||||||
(assert= 9 ([[3 6] [9 2]] 1 0))
|
(assert= 9 (ref [[3 6] [9 2]] 1 0))
|
||||||
|
|
||||||
($ a ['a' [[2 true] 2.3]])
|
($ a ['a' [[2 true] 2.3]])
|
||||||
|
|
||||||
(assert= 'a' (a 0))
|
(assert= 'a' (ref a 0))
|
||||||
(assert= 2 (a 1 0 0))
|
(assert= 2 (ref a 1 0 0))
|
||||||
|
|
||||||
($ (second arr)
|
($ (second arr)
|
||||||
(arr 1))
|
(ref arr 1))
|
||||||
|
|
||||||
(assert= 6 (second [2 6]))
|
(assert= 6 (second [2 6]))
|
||||||
|
|
||||||
|
@ -17,4 +17,4 @@
|
||||||
(assert= 4 (second (produce)))
|
(assert= 4 (second (produce)))
|
||||||
|
|
||||||
($ arr [2 'bim' produce false])
|
($ arr [2 'bim' produce false])
|
||||||
(assert= 6 (((arr 2)) 2))
|
(assert= 6 (ref ((ref arr 2)) 2))
|
|
@ -195,4 +195,29 @@ namespace fkstd
|
||||||
{
|
{
|
||||||
NUM_BINOP(!=);
|
NUM_BINOP(!=);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
STDRET array_ref(Loc loc, Module& mod, STDARGS args)
|
||||||
|
{
|
||||||
|
auto ref_val = args[0]->value();
|
||||||
|
size_t ref = std::get<size_t>(ref_val);
|
||||||
|
|
||||||
|
std::shared_ptr<Array> val =
|
||||||
|
std::get<std::shared_ptr<Array>>(mod.vm()->load_global(ref));
|
||||||
|
|
||||||
|
for (size_t i=1; i<args.size() - 1; i++)
|
||||||
|
{
|
||||||
|
int k = std::get<int>(args[i]->value());
|
||||||
|
|
||||||
|
auto ref_val = val->at(k)->value();
|
||||||
|
size_t ref = std::get<size_t>(ref_val);
|
||||||
|
|
||||||
|
auto arr =
|
||||||
|
std::get<std::shared_ptr<Array>>(mod.vm()->load_global(ref));
|
||||||
|
|
||||||
|
val = arr;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return val->at(std::get<int>(args.back()->value()));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,8 @@ namespace fkstd
|
||||||
STDRET ge(Loc loc, Module& mod, STDARGS args);
|
STDRET ge(Loc loc, Module& mod, STDARGS args);
|
||||||
STDRET eq(Loc loc, Module& mod, STDARGS args);
|
STDRET eq(Loc loc, Module& mod, STDARGS args);
|
||||||
STDRET ne(Loc loc, Module& mod, STDARGS args);
|
STDRET ne(Loc loc, Module& mod, STDARGS args);
|
||||||
|
|
||||||
|
STDRET array_ref(Loc loc, Module& mod, STDARGS args);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -18,6 +18,7 @@ extern "C" void lib(Module& mod)
|
||||||
mod.register_function(">=", fkstd::ge);
|
mod.register_function(">=", fkstd::ge);
|
||||||
mod.register_function("=", fkstd::eq);
|
mod.register_function("=", fkstd::eq);
|
||||||
mod.register_function("<>", fkstd::ne);
|
mod.register_function("<>", fkstd::ne);
|
||||||
|
mod.register_function("ref", fkstd::array_ref);
|
||||||
|
|
||||||
mod.register_macro("!", fkstd::set_addr);
|
mod.register_macro("!", fkstd::set_addr);
|
||||||
mod.register_macro("assert-static-fail", fkstd::assert_static_fail);
|
mod.register_macro("assert-static-fail", fkstd::assert_static_fail);
|
||||||
|
|
|
@ -218,12 +218,7 @@ namespace fk
|
||||||
compile_prog(node->child(i), prog);
|
compile_prog(node->child(i), prog);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (node->child(0)->type() == NODE_ARRAY)
|
if (node->child(0)->type() == NODE_LAMBDA
|
||||||
{
|
|
||||||
prog->add(OP_CALL_REF, node->size() - 1);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
else if (node->child(0)->type() == NODE_LAMBDA
|
|
||||||
|| node->child(0)->type() == NODE_CALL
|
|| node->child(0)->type() == NODE_CALL
|
||||||
|| node->child(0)->type() == NODE_NS)
|
|| node->child(0)->type() == NODE_NS)
|
||||||
{
|
{
|
||||||
|
@ -236,10 +231,9 @@ namespace fk
|
||||||
entry && entry->is_global() == false)
|
entry && entry->is_global() == false)
|
||||||
{
|
{
|
||||||
if (entry->node()
|
if (entry->node()
|
||||||
&& entry->node()->child(1)->type() != NODE_ARRAY
|
&& entry->node()
|
||||||
&& entry->node()->type() != NODE_ARRAY)
|
&& entry->node()->type() == NODE_LAMBDA)
|
||||||
{
|
{
|
||||||
std::cout << "-> " << entry->node()->string() << std::endl;
|
|
||||||
size_t arity = entry->node()->child(0)->size();
|
size_t arity = entry->node()->child(0)->size();
|
||||||
if (arity != node->size() - 1)
|
if (arity != node->size() - 1)
|
||||||
{
|
{
|
||||||
|
@ -264,6 +258,7 @@ namespace fk
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::cerr << "cannot call node '"
|
std::cerr << "cannot call node '"
|
||||||
<< node->string() << "'" << std::endl;
|
<< node->string() << "'" << std::endl;
|
||||||
abort();
|
abort();
|
||||||
|
|
25
src/VM.cpp
25
src/VM.cpp
|
@ -310,31 +310,6 @@ namespace fk
|
||||||
m_pc++;
|
m_pc++;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
else if (std::get_if<std::shared_ptr<Array>>(&val))
|
|
||||||
{
|
|
||||||
std::shared_ptr<Array> val =
|
|
||||||
std::get<std::shared_ptr<Array>>(load_global(ref));
|
|
||||||
|
|
||||||
for (size_t i=0; i<args.size() - 1; i++)
|
|
||||||
{
|
|
||||||
int k = std::get<int>(args[i]->value());
|
|
||||||
auto ref_val = val->at(k)->value();
|
|
||||||
|
|
||||||
size_t ref = std::get<size_t>(ref_val);
|
|
||||||
|
|
||||||
auto arr =
|
|
||||||
std::get<std::shared_ptr<Array>>(load_global(ref));
|
|
||||||
|
|
||||||
val = arr;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
push(frame().program->add
|
|
||||||
(val->at(std::get<int>(args.back()->value()))));
|
|
||||||
|
|
||||||
m_pc++;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto lambda = std::get<std::shared_ptr<Lambda>>(load_global(ref));
|
auto lambda = std::get<std::shared_ptr<Lambda>>(load_global(ref));
|
||||||
|
|
||||||
|
|
|
@ -23,6 +23,8 @@ namespace fk
|
||||||
};
|
};
|
||||||
class Module;
|
class Module;
|
||||||
|
|
||||||
|
FK_ERROR(execution_error);
|
||||||
|
|
||||||
class VM
|
class VM
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
|
Loading…
Reference in New Issue