diff --git a/tests/test_ASTNodeNaturalConversionChecker.cpp b/tests/test_ASTNodeNaturalConversionChecker.cpp index 373a0590955d494ad965c1fcba0790f50a1f4c9d..f37a58b410fd2b4213457f00f3336ae626c4c428 100644 --- a/tests/test_ASTNodeNaturalConversionChecker.cpp +++ b/tests/test_ASTNodeNaturalConversionChecker.cpp @@ -53,6 +53,18 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") data_node->m_data_type = ASTNodeDataType::bool_t; REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::string_t}); } + + SECTION("list -> string") + { + data_node->m_data_type = ASTNodeDataType::list_t; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::string_t}); + } + + SECTION("tuple -> string") + { + data_node->m_data_type = ASTNodeDataType::tuple_t; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::string_t}); + } } SECTION("-> R^d") @@ -221,6 +233,303 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::bool_t}); } } + + SECTION("-> tuple") + { + SECTION("B -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::bool_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::bool_t}}}); + } + + SECTION("B -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::bool_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}}); + } + + SECTION("N -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::unsigned_int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}}); + } + + SECTION("Z -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}}); + } + + SECTION("B -> tuple(Z)") + { + data_node->m_data_type = ASTNodeDataType::bool_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::int_t}}}); + } + + SECTION("N -> tuple(Z)") + { + data_node->m_data_type = ASTNodeDataType::unsigned_int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::int_t}}}); + } + + SECTION("Z -> tuple(Z)") + { + data_node->m_data_type = ASTNodeDataType::int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::int_t}}}); + } + + SECTION("B -> tuple(R)") + { + data_node->m_data_type = ASTNodeDataType::bool_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::double_t}}}); + } + + SECTION("N -> tuple(R)") + { + data_node->m_data_type = ASTNodeDataType::unsigned_int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::double_t}}}); + } + + SECTION("Z -> tuple(R)") + { + data_node->m_data_type = ASTNodeDataType::int_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::double_t}}}); + } + + SECTION("R -> tuple(R)") + { + data_node->m_data_type = ASTNodeDataType::double_t; + REQUIRE_NOTHROW( + ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ASTNodeDataType::double_t}}}); + } + + SECTION("R^1 -> tuple(R^1)") + { + auto R1 = ASTNodeDataType{ASTNodeDataType::vector_t, 1}; + data_node->m_data_type = R1; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, R1}}); + } + + SECTION("R^2 -> tuple(R^2)") + { + auto R2 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = R2; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, R2}}); + } + + SECTION("R^3 -> tuple(R^3)") + { + auto R3 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = R3; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, R3}}); + } + + SECTION("string -> tuple(string)") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::string_t}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::string_t}}); + } + + SECTION("type_id_t -> tuple(type_id_t)") + { + auto type_id = ASTNodeDataType{ASTNodeDataType::type_id_t, "foo"}; + data_node->m_data_type = type_id; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, type_id}); + } + + SECTION("(B, B, B) -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::bool_t}}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(B, N, Z) -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::unsigned_int_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::int_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(B, N, Z) -> tuple(Z)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::unsigned_int_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::int_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(R, N, Z) -> tuple(R)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::double_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::unsigned_int_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::int_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::double_t}}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(R^1, R^1) -> tuple(R^1)") + { + auto R1 = ASTNodeDataType{ASTNodeDataType::vector_t, 1}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = R1; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = R1; + data_node->emplace_back(std::move(list1_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, R1}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(R^2, R^2, R^2) -> tuple(R^2)") + { + auto R2 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = R2; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = R2; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = R2; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, R2}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(R^3, R^3) -> tuple(R^3)") + { + auto R3 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = R3; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = R3; + data_node->emplace_back(std::move(list1_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, R3}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(string, string) -> tuple(string)") + { + auto str_t = ASTNodeDataType{ASTNodeDataType::string_t}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = str_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = str_t; + data_node->emplace_back(std::move(list1_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, str_t}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + + SECTION("(type_id_t, type_id_t)-> tuple(type_id_t)") + { + auto type_id = ASTNodeDataType{ASTNodeDataType::type_id_t, "foo"}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = type_id; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = type_id; + data_node->emplace_back(std::move(list1_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, type_id}; + REQUIRE_NOTHROW(ASTNodeNaturalConversionChecker{*data_node, tuple_t}); + } + } } SECTION("Invalid conversions") @@ -361,6 +670,61 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") } } + SECTION("tuple -> R^d") + { + SECTION("tuple(N) -> R^1") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 1}}), + "invalid implicit conversion: tuple(N) -> R^1"); + } + + SECTION("tuple(R) -> R^1") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::double_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 1}}), + "invalid implicit conversion: tuple(R) -> R^1"); + } + + SECTION("tuple(R) -> R^2") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::double_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 2}}), + "invalid implicit conversion: tuple(R) -> R^2"); + } + + SECTION("tuple(B) -> R^2") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::bool_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 2}}), + "invalid implicit conversion: tuple(B) -> R^2"); + } + + SECTION("tuple(Z) -> R^3") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 3}}), + "invalid implicit conversion: tuple(Z) -> R^3"); + } + + SECTION("tuple(R) -> R^3") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::double_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::vector_t, 3}}), + "invalid implicit conversion: tuple(R) -> R^3"); + } + } + SECTION("R -> R^d") { data_node->m_data_type = ASTNodeDataType::double_t; @@ -526,6 +890,21 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::double_t}), "invalid implicit conversion: R^3 -> R"); } + + SECTION("tuple(N) -> R") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::double_t}), + "invalid implicit conversion: tuple(N) -> R"); + } + + SECTION("tuple(R) -> R") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::double_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::double_t}), + "invalid implicit conversion: tuple(R) -> R"); + } } SECTION("-> Z") @@ -564,6 +943,21 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::int_t}), "invalid implicit conversion: R -> Z"); } + + SECTION("tuple(N) -> Z") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::int_t}), + "invalid implicit conversion: tuple(N) -> Z"); + } + + SECTION("tuple(Z) -> Z") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::int_t}), + "invalid implicit conversion: tuple(Z) -> Z"); + } } SECTION("-> N") @@ -602,6 +996,21 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::unsigned_int_t}), "invalid implicit conversion: R -> N"); } + + SECTION("tuple(Z) -> N") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::unsigned_int_t}), + "invalid implicit conversion: tuple(Z) -> N"); + } + + SECTION("tuple(N) -> N") + { + data_node->m_data_type = + ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::unsigned_int_t}), + "invalid implicit conversion: tuple(N) -> N"); + } } SECTION("-> B") @@ -647,12 +1056,215 @@ TEST_CASE("ASTNodeNaturalConversionChecker", "[language]") REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::bool_t}), "invalid implicit conversion: Z -> B"); } + SECTION("N -> B") { data_node->m_data_type = ASTNodeDataType::unsigned_int_t; REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::bool_t}), "invalid implicit conversion: N -> B"); } + + SECTION("tuple(Z) -> B") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::bool_t}), + "invalid implicit conversion: tuple(Z) -> B"); + } + + SECTION("tuple(B) -> B") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::bool_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType::bool_t}), + "invalid implicit conversion: tuple(B) -> B"); + } + } + + SECTION("-> tuple") + { + SECTION("N -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::unsigned_int_t; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: N -> tuple(B)"); + } + + SECTION("Z -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::int_t; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: Z -> tuple(B)"); + } + + SECTION("R -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::double_t; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: R -> tuple(B)"); + } + + SECTION("string -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType::string_t; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: string -> tuple(B)"); + } + + SECTION("R^1 -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::vector_t, 1}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: R^1 -> tuple(B)"); + } + + SECTION("R^2 -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: R^2 -> tuple(B)"); + } + + SECTION("R^3 -> tuple(B)") + { + data_node->m_data_type = ASTNodeDataType{ASTNodeDataType::vector_t, 3}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::bool_t}}}), + "invalid implicit conversion: R^3 -> tuple(B)"); + } + + SECTION("R -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::double_t; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, + ASTNodeDataType{ + ASTNodeDataType::unsigned_int_t}}}), + "invalid implicit conversion: R -> tuple(N)"); + } + + SECTION("R^1 -> tuple(R^2)") + { + auto R1 = ASTNodeDataType{ASTNodeDataType::vector_t, 1}; + auto R2 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = R1; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, R2}}), + "invalid implicit conversion: R^1 -> tuple(R^2)"); + } + + SECTION("R^2 -> tuple(R^3)") + { + auto R2 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + auto R3 = ASTNodeDataType{ASTNodeDataType::vector_t, 3}; + data_node->m_data_type = R2; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, R3}}), + "invalid implicit conversion: R^2 -> tuple(R^3)"); + } + + SECTION("R^3 -> tuple(R^2)") + { + auto R3 = ASTNodeDataType{ASTNodeDataType::vector_t, 3}; + auto R2 = ASTNodeDataType{ASTNodeDataType::vector_t, 2}; + data_node->m_data_type = R3; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, + ASTNodeDataType{ASTNodeDataType::tuple_t, R2}}), + "invalid implicit conversion: R^3 -> tuple(R^2)"); + } + + SECTION("(B, R, Z) -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::double_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::int_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, tuple_t}), + "invalid implicit conversion: R -> N"); + } + + SECTION("(R, N, Z) -> tuple(Z)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::double_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::unsigned_int_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::int_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, tuple_t}), + "invalid implicit conversion: R -> Z"); + } + + SECTION("(B, N, R) -> tuple(N)") + { + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = ASTNodeDataType::bool_t; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = ASTNodeDataType::unsigned_int_t; + data_node->emplace_back(std::move(list1_node)); + + std::unique_ptr list2_node = std::make_unique<ASTNode>(); + list2_node->m_data_type = ASTNodeDataType::double_t; + data_node->emplace_back(std::move(list2_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, ASTNodeDataType{ASTNodeDataType::unsigned_int_t}}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, tuple_t}), + "invalid implicit conversion: R -> N"); + } + } + + SECTION("(type_id_t, type_id_t) -> tuple(type_id_t)") + { + auto type_id1 = ASTNodeDataType{ASTNodeDataType::type_id_t, "foo"}; + auto type_id2 = ASTNodeDataType{ASTNodeDataType::type_id_t, "bar"}; + data_node->m_data_type = ASTNodeDataType::list_t; + { + std::unique_ptr list0_node = std::make_unique<ASTNode>(); + list0_node->m_data_type = type_id1; + data_node->emplace_back(std::move(list0_node)); + + std::unique_ptr list1_node = std::make_unique<ASTNode>(); + list1_node->m_data_type = type_id2; + data_node->emplace_back(std::move(list1_node)); + } + auto tuple_t = ASTNodeDataType{ASTNodeDataType::tuple_t, type_id2}; + REQUIRE_THROWS_WITH((ASTNodeNaturalConversionChecker{*data_node, tuple_t}), + "invalid implicit conversion: foo -> bar"); } } }