Moved from Value::from constructor to Value constructor
This commit is contained in:
parent
6a98178690
commit
5a7c204ceb
@ -72,7 +72,7 @@ static Result<Value> ctx_read_write_property(Interpreter &interpreter, std::vect
|
||||
using Member_Type = std::remove_cvref_t<decltype(std::declval<Context>().*(Mem_Ptr))>;
|
||||
|
||||
if (args.size() == 0) {
|
||||
return Value::from(Number(interpreter.context_stack.back().*(Mem_Ptr)));
|
||||
return Number(interpreter.context_stack.back().*(Mem_Ptr));
|
||||
}
|
||||
|
||||
assert(std::holds_alternative<Number>(args.front().data), "Ctx only holds numeric values");
|
||||
@ -130,7 +130,7 @@ static Result<Value> apply_numeric_transform(Interpreter &i, std::vector<Value>
|
||||
{
|
||||
if (args.size()) {
|
||||
if (auto number = get_if<Number>(args.front().data)) {
|
||||
return Value::from((number->*Method)());
|
||||
return (number->*Method)();
|
||||
}
|
||||
}
|
||||
|
||||
@ -142,7 +142,7 @@ static Result<Value> apply_numeric_transform(Interpreter &i, std::vector<Value>
|
||||
goto invalid_argument_type;
|
||||
}
|
||||
}
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
|
||||
|
||||
invalid_argument_type:
|
||||
@ -185,14 +185,14 @@ static Result<Value> builtin_range(Interpreter&, std::vector<Value> args)
|
||||
Array array;
|
||||
if constexpr (dir == Range_Direction::Up) {
|
||||
for (; start < stop; start += step) {
|
||||
array.elements.push_back(Value::from(start));
|
||||
array.elements.push_back(start);
|
||||
}
|
||||
} else {
|
||||
for (; start < stop; start += step) {
|
||||
array.elements.push_back(Value::from(stop - start - Number(1)));
|
||||
array.elements.push_back(stop - start - Number(1));
|
||||
}
|
||||
}
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Send MIDI Program Change message
|
||||
@ -444,7 +444,7 @@ static Result<Value> builtin_primes(Interpreter&, std::vector<Value> args)
|
||||
// Better sieve could be Sieve of Atkin, but it's more complicated
|
||||
// so for now we would use Eratosthenes one.
|
||||
if (n_frac.simplify_inplace(); n_frac.num <= 1) {
|
||||
return Value::from(Array{});
|
||||
return Array{};
|
||||
}
|
||||
size_t n = n_frac.floor().as_int();
|
||||
|
||||
@ -468,10 +468,10 @@ static Result<Value> builtin_primes(Interpreter&, std::vector<Value> args)
|
||||
|
||||
for (uint i = 2; i < sieve.size() && results.size() != n; ++i) {
|
||||
if (!sieve[i]) {
|
||||
results.push_back(Value::from(Number(i)));
|
||||
results.push_back(Number(i));
|
||||
}
|
||||
}
|
||||
return Value::from(Array(std::move(results)));
|
||||
return results;
|
||||
}
|
||||
|
||||
return Error {
|
||||
@ -613,14 +613,14 @@ static Result<Value> builtin_update(Interpreter &i, std::vector<Value> args)
|
||||
if (auto a = match<Array, Number, Value>(args)) {
|
||||
auto& [v, index, value] = *a;
|
||||
v.elements[index.as_int()] = std::move(std::move(value));
|
||||
return Value::from(std::move(v));
|
||||
return std::move(v);
|
||||
}
|
||||
|
||||
if (auto a = match<Block, Number, Value>(args)) {
|
||||
auto& [v, index, value] = *a;
|
||||
auto array = Try(flatten(i, { Value::from(std::move(v)) }));
|
||||
auto array = Try(flatten(i, { std::move(v) }));
|
||||
array[index.as_int()] = std::move(args.back());
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
return guard.yield_error();
|
||||
@ -630,7 +630,7 @@ static Result<Value> builtin_update(Interpreter &i, std::vector<Value> args)
|
||||
static Result<Value> builtin_typeof(Interpreter&, std::vector<Value> args)
|
||||
{
|
||||
assert(args.size() == 1, "typeof expects only one argument"); // TODO(assert)
|
||||
return Value::from(Symbol(type_name(args.front())));
|
||||
return Symbol(type_name(args.front()));
|
||||
}
|
||||
|
||||
/// Return length of container or set/get default length to play
|
||||
@ -638,7 +638,7 @@ static Result<Value> builtin_len(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
if (args.size() == 1) {
|
||||
if (auto coll = get_if<Collection>(args.front())) {
|
||||
return Value::from(Number(coll->size()));
|
||||
return Number(coll->size());
|
||||
}
|
||||
}
|
||||
// TODO Add overload that tells length of array to error reporting
|
||||
@ -648,7 +648,7 @@ static Result<Value> builtin_len(Interpreter &i, std::vector<Value> args)
|
||||
/// Join arguments into flat array
|
||||
static Result<Value> builtin_flat(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
return Value::from(Try(into_flat_array(i, std::move(args))));
|
||||
return Try(into_flat_array(i, std::move(args)));
|
||||
}
|
||||
|
||||
/// Shuffle arguments
|
||||
@ -657,7 +657,7 @@ static Result<Value> builtin_shuffle(Interpreter &i, std::vector<Value> args)
|
||||
static std::mt19937 rnd{std::random_device{}()};
|
||||
auto array = Try(flatten(i, std::move(args)));
|
||||
std::shuffle(array.begin(), array.end(), rnd);
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Permute arguments
|
||||
@ -665,7 +665,7 @@ static Result<Value> builtin_permute(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
auto array = Try(flatten(i, std::move(args)));
|
||||
std::next_permutation(array.begin(), array.end());
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Sort arguments
|
||||
@ -673,7 +673,7 @@ static Result<Value> builtin_sort(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
auto array = Try(flatten(i, std::move(args)));
|
||||
std::sort(array.begin(), array.end());
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Reverse arguments
|
||||
@ -681,7 +681,7 @@ static Result<Value> builtin_reverse(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
auto array = Try(flatten(i, std::move(args)));
|
||||
std::reverse(array.begin(), array.end());
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Get minimum of arguments
|
||||
@ -724,10 +724,10 @@ static Result<Value> builtin_partition(Interpreter &i, std::vector<Value> args)
|
||||
tuple[Try(predicate(i, { std::move(value) })).truthy()].elements.push_back(std::move(value));
|
||||
}
|
||||
|
||||
return Value::from(Array {{
|
||||
Value::from(std::move(tuple[true])),
|
||||
Value::from(std::move(tuple[false]))
|
||||
}});
|
||||
return Array {{
|
||||
std::move(tuple[true]),
|
||||
std::move(tuple[false])
|
||||
}};
|
||||
}
|
||||
|
||||
/// Rotate arguments by n steps
|
||||
@ -750,7 +750,7 @@ static Result<Value> builtin_rotate(Interpreter &i, std::vector<Value> args)
|
||||
offset = -offset % array.size();
|
||||
std::rotate(array.rbegin(), array.rbegin() + offset, array.rend());
|
||||
}
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
}
|
||||
|
||||
@ -770,7 +770,7 @@ static Result<Value> builtin_unique(Interpreter &i, std::vector<Value> args)
|
||||
result.push_back(std::move(el));
|
||||
}
|
||||
}
|
||||
return Value::from(std::move(result));
|
||||
return result;
|
||||
}
|
||||
|
||||
/// Returns arguments with all successive copies eliminated
|
||||
@ -787,16 +787,16 @@ static Result<Value> builtin_uniq(Interpreter &i, std::vector<Value> args)
|
||||
result.push_back(el);
|
||||
previous = std::move(el);
|
||||
}
|
||||
return Value::from(std::move(result));
|
||||
return result;
|
||||
}
|
||||
|
||||
static Result<Value> builtin_hash(Interpreter&, std::vector<Value> args)
|
||||
{
|
||||
return Value::from(Number(
|
||||
return Number(
|
||||
std::accumulate(args.cbegin(), args.cend(), size_t(0), [](size_t h, Value const& v) {
|
||||
return hash_combine(h, std::hash<Value>{}(v));
|
||||
})
|
||||
));
|
||||
);
|
||||
}
|
||||
|
||||
/// Build chord from arguments
|
||||
@ -804,7 +804,7 @@ static Result<Value> builtin_chord(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
Chord chord;
|
||||
Try(create_chord(chord.notes, i, std::move(args)));
|
||||
return Value::from(std::move(chord));
|
||||
return chord;
|
||||
}
|
||||
|
||||
/// Send MIDI message Note On
|
||||
@ -918,7 +918,7 @@ static Result<Value> builtin_mix(Interpreter &i, std::vector<Value> args)
|
||||
}
|
||||
} while (awaiting_containers);
|
||||
|
||||
return Value::from(std::move(result));
|
||||
return result;
|
||||
}
|
||||
|
||||
/// Call operator. Calls first argument with remaining arguments
|
||||
|
@ -17,7 +17,7 @@ static Result<Value> vectorize(auto &&operation, Interpreter &interpreter, Value
|
||||
array.elements.push_back(
|
||||
Try(operation(interpreter, { Try(lhs_coll->index(interpreter, i)), rhs })));
|
||||
}
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
assert(rhs_coll != nullptr, "Trying to vectorize two non-collections");
|
||||
@ -27,7 +27,7 @@ static Result<Value> vectorize(auto &&operation, Interpreter &interpreter, Value
|
||||
array.elements.push_back(
|
||||
Try(operation(interpreter, { lhs, Try(rhs_coll->index(interpreter, i)) })));
|
||||
}
|
||||
return Value::from(std::move(array));
|
||||
return array;
|
||||
}
|
||||
|
||||
/// Intrinsic implementation primitive to ease operation vectorization
|
||||
@ -61,13 +61,13 @@ template<typename Binary_Operation>
|
||||
static Result<Value> plus_minus_operator(Interpreter &interpreter, std::vector<Value> args)
|
||||
{
|
||||
if (args.empty()) {
|
||||
return Value::from(Number(0));
|
||||
return Number(0);
|
||||
}
|
||||
|
||||
Value init = args.front();
|
||||
return algo::fold(std::span(args).subspan(1), std::move(init), [&interpreter](Value lhs, Value &rhs) -> Result<Value> {
|
||||
if (auto a = match<Number, Number>(lhs, rhs)) {
|
||||
return Value::from(std::apply(Binary_Operation{}, *a));
|
||||
return std::apply(Binary_Operation{}, *a);
|
||||
}
|
||||
|
||||
auto result = symetric<Chord, Number>(lhs, rhs, [](Chord &lhs, Number rhs) {
|
||||
@ -77,7 +77,7 @@ static Result<Value> plus_minus_operator(Interpreter &interpreter, std::vector<V
|
||||
note.simplify_inplace();
|
||||
}
|
||||
}
|
||||
return Value::from(lhs);
|
||||
return lhs;
|
||||
});
|
||||
if (result.has_value()) {
|
||||
return *std::move(result);
|
||||
@ -110,13 +110,13 @@ static Result<Value> binary_operator(Interpreter& interpreter, std::vector<Value
|
||||
{
|
||||
static constexpr char Name[] = { Chars..., '\0' };
|
||||
if (args.empty()) {
|
||||
return Value::from(Number(1));
|
||||
return Number(1);
|
||||
}
|
||||
auto init = std::move(args.front());
|
||||
return algo::fold(std::span(args).subspan(1), std::move(init),
|
||||
[&interpreter](Value lhs, Value &rhs) -> Result<Value> {
|
||||
if (auto a = match<Number, Number>(lhs, rhs)) {
|
||||
return wrap_value(std::apply(Binary_Operation{}, *a));
|
||||
return std::apply(Binary_Operation{}, *a);
|
||||
}
|
||||
|
||||
if (holds_alternative<Collection>(lhs) != holds_alternative<Collection>(rhs)) {
|
||||
@ -140,7 +140,7 @@ template<typename Binary_Predicate>
|
||||
static Result<Value> comparison_operator(Interpreter &interpreter, std::vector<Value> args)
|
||||
{
|
||||
if (args.size() != 2) {
|
||||
return Value::from(algo::pairwise_all(std::move(args), Binary_Predicate{}));
|
||||
return algo::pairwise_all(std::move(args), Binary_Predicate{});
|
||||
}
|
||||
|
||||
auto lhs_coll = get_if<Collection>(args.front());
|
||||
@ -153,32 +153,30 @@ static Result<Value> comparison_operator(Interpreter &interpreter, std::vector<V
|
||||
std::vector<Value> result;
|
||||
result.reserve(coll->size());
|
||||
for (auto i = 0u; i < coll->size(); ++i) {
|
||||
result.push_back(
|
||||
Value::from(
|
||||
Binary_Predicate{}(
|
||||
Try(coll->index(interpreter, i)),
|
||||
*element
|
||||
)
|
||||
)
|
||||
result.push_back(Value(
|
||||
Binary_Predicate{}(
|
||||
Try(coll->index(interpreter, i)),
|
||||
*element
|
||||
))
|
||||
);
|
||||
}
|
||||
return Value::from(Array { std::move(result) });
|
||||
return Array { std::move(result) };
|
||||
}
|
||||
|
||||
return Value::from(Binary_Predicate{}(std::move(args.front()), std::move(args.back())));
|
||||
return Binary_Predicate{}(std::move(args.front()), std::move(args.back()));
|
||||
}
|
||||
|
||||
static Result<Value> multiplication_operator(Interpreter &i, std::vector<Value> args)
|
||||
{
|
||||
if (args.empty()) {
|
||||
return Value::from(Number(1));
|
||||
return Number(1);
|
||||
}
|
||||
|
||||
auto init = std::move(args.front());
|
||||
return algo::fold(std::span(args).subspan(1), std::move(init), [&i](Value lhs, Value &rhs) -> Result<Value> {
|
||||
{
|
||||
auto result = symetric<Number, Chord>(lhs, rhs, [](Number lhs, Chord &rhs) {
|
||||
return Value::from(Array { std::vector<Value>(lhs.floor().as_int(), Value::from(std::move(rhs))) });
|
||||
return Array { std::vector<Value>(lhs.floor().as_int(), std::move(rhs)) };
|
||||
});
|
||||
|
||||
if (result.has_value()) {
|
||||
@ -250,7 +248,7 @@ static constexpr auto Operators = std::array {
|
||||
result.push_back(Try(source.index(interpreter, *index)));
|
||||
}
|
||||
}
|
||||
return Value::from(Array(std::move(result)));
|
||||
return Array(std::move(result));
|
||||
}
|
||||
|
||||
return Error {
|
||||
@ -290,7 +288,7 @@ static constexpr auto Operators = std::array {
|
||||
l.reserve(l.size() + r.size());
|
||||
std::move(r.begin(), r.end(), std::back_inserter(l));
|
||||
|
||||
return Value::from(lhs);
|
||||
return lhs;
|
||||
}
|
||||
|
||||
auto result = Array {};
|
||||
@ -300,7 +298,7 @@ static constexpr auto Operators = std::array {
|
||||
result.elements.push_back(Try(array.index(i, n)));
|
||||
}
|
||||
}
|
||||
return Value::from(std::move(result));
|
||||
return result;
|
||||
}
|
||||
},
|
||||
};
|
||||
|
@ -32,11 +32,11 @@ struct Interpreter::Incoming_Midi_Callbacks
|
||||
target = [interpreter = &i, callback = &callback](T ...source_args)
|
||||
{
|
||||
if (!std::holds_alternative<Nil>(callback->data)) {
|
||||
std::vector<Value> args { Value::from(Number(source_args))... };
|
||||
args[1] = Value::from(Chord { { Note {
|
||||
std::vector<Value> args { Number(source_args)... };
|
||||
args[1] = Note {
|
||||
.base = i32(std::get<Number>(args[1].data).num % 12),
|
||||
.octave = std::get<Number>(args[1].data).num / 12
|
||||
}}});
|
||||
};
|
||||
auto result = (*callback)(*interpreter, std::move(args));
|
||||
// We discard this since callback is running in another thread.
|
||||
(void) result;
|
||||
@ -47,7 +47,7 @@ struct Interpreter::Incoming_Midi_Callbacks
|
||||
target = [interpreter = &i, callback = &callback](T ...source_args)
|
||||
{
|
||||
if (!std::holds_alternative<Nil>(callback->data)) {
|
||||
auto result = (*callback)(*interpreter, { Value::from(Number(source_args))... });
|
||||
auto result = (*callback)(*interpreter, { Number(source_args)... });
|
||||
// We discard this since callback is running in another thread.
|
||||
(void) result;
|
||||
}
|
||||
|
@ -12,21 +12,21 @@
|
||||
static inline void register_note_length_constants()
|
||||
{
|
||||
auto &global = *Env::global;
|
||||
global.force_define("fn", Value::from(Number(1, 1)));
|
||||
global.force_define("dfn", Value::from(Number(3, 2)));
|
||||
global.force_define("hn", Value::from(Number(1, 2)));
|
||||
global.force_define("dhn", Value::from(Number(3, 4)));
|
||||
global.force_define("ddhn", Value::from(Number(7, 8)));
|
||||
global.force_define("qn", Value::from(Number(1, 4)));
|
||||
global.force_define("dqn", Value::from(Number(3, 8)));
|
||||
global.force_define("ddqn", Value::from(Number(7, 16)));
|
||||
global.force_define("en", Value::from(Number(1, 8)));
|
||||
global.force_define("den", Value::from(Number(3, 16)));
|
||||
global.force_define("dden", Value::from(Number(7, 32)));
|
||||
global.force_define("sn", Value::from(Number(1, 16)));
|
||||
global.force_define("dsn", Value::from(Number(3, 32)));
|
||||
global.force_define("tn", Value::from(Number(1, 32)));
|
||||
global.force_define("dtn", Value::from(Number(3, 64)));
|
||||
global.force_define("fn", Number(1, 1));
|
||||
global.force_define("dfn", Number(3, 2));
|
||||
global.force_define("hn", Number(1, 2));
|
||||
global.force_define("dhn", Number(3, 4));
|
||||
global.force_define("ddhn", Number(7, 8));
|
||||
global.force_define("qn", Number(1, 4));
|
||||
global.force_define("dqn", Number(3, 8));
|
||||
global.force_define("ddqn", Number(7, 16));
|
||||
global.force_define("en", Number(1, 8));
|
||||
global.force_define("den", Number(3, 16));
|
||||
global.force_define("dden", Number(7, 32));
|
||||
global.force_define("sn", Number(1, 16));
|
||||
global.force_define("dsn", Number(3, 32));
|
||||
global.force_define("tn", Number(1, 32));
|
||||
global.force_define("dtn", Number(3, 64));
|
||||
}
|
||||
|
||||
Interpreter::Interpreter()
|
||||
@ -60,7 +60,7 @@ Result<Value> Interpreter::eval(Ast &&ast)
|
||||
if (auto op = operators.find(std::string(ast.token.source.substr(1))); op != operators.end()) {
|
||||
return Value(op->second);
|
||||
} else {
|
||||
return Value::from(std::move(ast.token.source).substr(1));
|
||||
return std::move(ast.token.source).substr(1);
|
||||
}
|
||||
}
|
||||
|
||||
@ -201,7 +201,7 @@ Result<Value> Interpreter::eval(Ast &&ast)
|
||||
|
||||
block.context = env;
|
||||
block.body = std::move(ast.arguments.back());
|
||||
return Value::from(std::move(block));
|
||||
return block;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -111,18 +111,17 @@ Result<Value> Chord::operator()(Interpreter& interpreter, std::vector<Value> arg
|
||||
|
||||
if (auto chord = get_if<Chord>(arg)) {
|
||||
std::transform(current.begin(), current.end(), std::back_inserter(array),
|
||||
[](Chord &c) { return Value::from(std::move(c)); });
|
||||
[](Chord &c) { return std::move(c); });
|
||||
current.clear();
|
||||
current.push_back(std::move(*chord));
|
||||
state = Waiting_For_Octave;
|
||||
}
|
||||
}
|
||||
|
||||
std::transform(current.begin(), current.end(), std::back_inserter(array),
|
||||
[](Chord &c) { return Value::from(std::move(c)); });
|
||||
std::move(current.begin(), current.end(), std::back_inserter(array));
|
||||
|
||||
assert(not array.empty(), "At least *this should be in this array");
|
||||
return Value::from(Array{std::move(array)});
|
||||
return array;
|
||||
}
|
||||
|
||||
std::ostream& operator<<(std::ostream& os, Chord const& chord)
|
||||
|
@ -14,99 +14,79 @@ Result<Value> Value::from(Token t)
|
||||
{
|
||||
switch (t.type) {
|
||||
case Token::Type::Numeric:
|
||||
return Value::from(Try(Number::from(std::move(t))));
|
||||
return Try(Number::from(std::move(t)));
|
||||
|
||||
case Token::Type::Symbol:
|
||||
return Value::from(std::string(t.source));
|
||||
return t.source;
|
||||
|
||||
case Token::Type::Keyword:
|
||||
if (t.source == "false") return Value::from(false);
|
||||
if (t.source == "nil") return Value{};
|
||||
if (t.source == "true") return Value::from(true);
|
||||
if (t.source == "false") return false;
|
||||
if (t.source == "nil") return {};
|
||||
if (t.source == "true") return true;
|
||||
unreachable();
|
||||
|
||||
case Token::Type::Chord:
|
||||
if (t.source.size() == 1 || (t.source.size() == 2 && t.source.back() == '#')) {
|
||||
auto maybe_note = Note::from(t.source);
|
||||
assert(maybe_note.has_value(), "Somehow parser passed invalid note literal");
|
||||
return Value::from(*maybe_note);
|
||||
return *maybe_note;
|
||||
}
|
||||
|
||||
return Value::from(Chord::from(t.source));
|
||||
return Chord::from(t.source);
|
||||
|
||||
default:
|
||||
unreachable();
|
||||
}
|
||||
}
|
||||
|
||||
Value Value::from(Explicit_Bool b)
|
||||
Value::Value(Explicit_Bool b)
|
||||
: data{b.value}
|
||||
{
|
||||
Value v;
|
||||
v.data = b.value;
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(Number n)
|
||||
Value::Value(Number n)
|
||||
: data(n.simplify())
|
||||
{
|
||||
Value v;
|
||||
v.data = std::move(n).simplify();
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(std::string s)
|
||||
Value::Value(std::string s)
|
||||
: data(Symbol(std::move(s)))
|
||||
{
|
||||
Value v;
|
||||
v.data = Symbol(std::move(s));
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(std::string_view s)
|
||||
Value::Value(std::string_view s)
|
||||
: data(Symbol(s))
|
||||
{
|
||||
Value v;
|
||||
v.data = Symbol(std::move(s));
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(char const* s)
|
||||
Value::Value(char const* s)
|
||||
: data(Symbol(s))
|
||||
{
|
||||
Value v;
|
||||
v.data = Symbol(s);
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(Block &&block)
|
||||
Value::Value(Block &&block)
|
||||
: data{std::move(block)}
|
||||
{
|
||||
Value v;
|
||||
v.data = std::move(block);
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(Array &&array)
|
||||
Value::Value(Array &&array)
|
||||
: data{std::move(array)}
|
||||
{
|
||||
Value v;
|
||||
v.data = std::move(array);
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(std::vector<Value> &&array)
|
||||
Value::Value(std::vector<Value> &&array)
|
||||
: data(Array(std::move(array)))
|
||||
{
|
||||
Value v;
|
||||
v.data = Array(std::move(array));
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(Note n)
|
||||
Value::Value(Note n)
|
||||
: data(Chord(n))
|
||||
{
|
||||
Value v;
|
||||
v.data = Chord(n);
|
||||
return v;
|
||||
}
|
||||
|
||||
Value Value::from(Chord chord)
|
||||
Value::Value(Chord chord)
|
||||
: data(std::move(chord))
|
||||
{
|
||||
Value v;
|
||||
v.data = std::move(chord);
|
||||
return v;
|
||||
}
|
||||
|
||||
Result<Value> Value::operator()(Interpreter &i, std::vector<Value> args) const
|
||||
|
@ -28,17 +28,17 @@ struct Value
|
||||
/// Create value holding provided boolean
|
||||
///
|
||||
/// Using Explicit_Bool to prevent from implicit casts
|
||||
static Value from(Explicit_Bool b);
|
||||
Value(Explicit_Bool b);
|
||||
|
||||
static Value from(Array &&array); ///< Create value of type array holding provided array
|
||||
static Value from(Block &&l); ///< Create value of type block holding provided block
|
||||
static Value from(Chord chord); ///< Create value of type music holding provided chord
|
||||
static Value from(Note n); ///< Create value of type music holding provided note
|
||||
static Value from(Number n); ///< Create value of type number holding provided number
|
||||
static Value from(char const* s); ///< Create value of type symbol holding provided symbol
|
||||
static Value from(std::string s); ///< Create value of type symbol holding provided symbol
|
||||
static Value from(std::string_view s); ///< Create value of type symbol holding provided symbol
|
||||
static Value from(std::vector<Value> &&array); ///< Create value of type array holding provided array
|
||||
Value(Array &&array); ///< Create value of type array holding provided array
|
||||
Value(Block &&l); ///< Create value of type block holding provided block
|
||||
Value(Chord chord); ///< Create value of type music holding provided chord
|
||||
Value(Note n); ///< Create value of type music holding provided note
|
||||
Value(Number n); ///< Create value of type number holding provided number
|
||||
Value(char const* s); ///< Create value of type symbol holding provided symbol
|
||||
Value(std::string s); ///< Create value of type symbol holding provided symbol
|
||||
Value(std::string_view s); ///< Create value of type symbol holding provided symbol
|
||||
Value(std::vector<Value> &&array); ///< Create value of type array holding provided array
|
||||
|
||||
// TODO Most strings should not be allocated by Value, but reference to string allocated previously
|
||||
// Wrapper for std::string is needed that will allocate only when needed, middle ground between:
|
||||
@ -107,12 +107,7 @@ template<> struct std::hash<Value> { std::size_t operator()(Value const&) cons
|
||||
template<typename T>
|
||||
Result<Value> wrap_value(Result<T> &&value)
|
||||
{
|
||||
return std::move(value).map([](auto &&value) { return Value::from(std::move(value)); });
|
||||
}
|
||||
|
||||
Value wrap_value(auto &&value)
|
||||
{
|
||||
return Value::from(std::move(value));
|
||||
return std::move(value).map([](auto &&value) { return Value(std::move(value)); });
|
||||
}
|
||||
|
||||
template<typename Desired>
|
||||
|
Loading…
Reference in New Issue
Block a user