@@ -1093,3 +1093,120 @@ TEST(JSON_object, reorder_already_ordered) {
10931093 EXPECT_EQ (iterator->first , " cherry" );
10941094 EXPECT_EQ (iterator->second .to_integer (), 3 );
10951095}
1096+
1097+ TEST (JSON_object, try_at_start_hit) {
1098+ const sourcemeta::core::JSON document =
1099+ sourcemeta::core::parse_json (" {\" foo\" :1,\" bar\" :2,\" baz\" :3}" );
1100+ const auto &object{document.as_object ()};
1101+ sourcemeta::core::JSON::Object::size_type start{0 };
1102+
1103+ const auto hash_foo{object.hash (" foo" )};
1104+ const auto *result_foo{object.try_at (" foo" , hash_foo, start)};
1105+ EXPECT_TRUE (result_foo);
1106+ EXPECT_EQ (result_foo->to_integer (), 1 );
1107+ EXPECT_EQ (start, 1 );
1108+
1109+ const auto hash_bar{object.hash (" bar" )};
1110+ const auto *result_bar{object.try_at (" bar" , hash_bar, start)};
1111+ EXPECT_TRUE (result_bar);
1112+ EXPECT_EQ (result_bar->to_integer (), 2 );
1113+ EXPECT_EQ (start, 2 );
1114+
1115+ const auto hash_baz{object.hash (" baz" )};
1116+ const auto *result_baz{object.try_at (" baz" , hash_baz, start)};
1117+ EXPECT_TRUE (result_baz);
1118+ EXPECT_EQ (result_baz->to_integer (), 3 );
1119+ EXPECT_EQ (start, 3 );
1120+ }
1121+
1122+ TEST (JSON_object, try_at_start_miss) {
1123+ const sourcemeta::core::JSON document =
1124+ sourcemeta::core::parse_json (" {\" foo\" :1,\" bar\" :2}" );
1125+ const auto &object{document.as_object ()};
1126+ sourcemeta::core::JSON::Object::size_type start{0 };
1127+
1128+ const auto hash_missing{object.hash (" missing" )};
1129+ const auto *result{object.try_at (" missing" , hash_missing, start)};
1130+ EXPECT_FALSE (result);
1131+ EXPECT_EQ (start, 0 );
1132+ }
1133+
1134+ TEST (JSON_object, try_at_start_reverse_order) {
1135+ const sourcemeta::core::JSON document =
1136+ sourcemeta::core::parse_json (" {\" foo\" :1,\" bar\" :2,\" baz\" :3}" );
1137+ const auto &object{document.as_object ()};
1138+ sourcemeta::core::JSON::Object::size_type start{0 };
1139+
1140+ const auto hash_baz{object.hash (" baz" )};
1141+ const auto *result_baz{object.try_at (" baz" , hash_baz, start)};
1142+ EXPECT_TRUE (result_baz);
1143+ EXPECT_EQ (result_baz->to_integer (), 3 );
1144+ EXPECT_EQ (start, 3 );
1145+
1146+ const auto hash_bar{object.hash (" bar" )};
1147+ const auto *result_bar{object.try_at (" bar" , hash_bar, start)};
1148+ EXPECT_TRUE (result_bar);
1149+ EXPECT_EQ (result_bar->to_integer (), 2 );
1150+ EXPECT_EQ (start, 2 );
1151+
1152+ const auto hash_foo{object.hash (" foo" )};
1153+ const auto *result_foo{object.try_at (" foo" , hash_foo, start)};
1154+ EXPECT_TRUE (result_foo);
1155+ EXPECT_EQ (result_foo->to_integer (), 1 );
1156+ EXPECT_EQ (start, 1 );
1157+ }
1158+
1159+ TEST (JSON_object, try_at_start_single_property) {
1160+ const sourcemeta::core::JSON document =
1161+ sourcemeta::core::parse_json (" {\" only\" :42}" );
1162+ const auto &object{document.as_object ()};
1163+ sourcemeta::core::JSON::Object::size_type start{0 };
1164+
1165+ const auto hash_only{object.hash (" only" )};
1166+ const auto *result{object.try_at (" only" , hash_only, start)};
1167+ EXPECT_TRUE (result);
1168+ EXPECT_EQ (result->to_integer (), 42 );
1169+ EXPECT_EQ (start, 1 );
1170+ }
1171+
1172+ TEST (JSON_object, try_at_start_wraparound) {
1173+ const sourcemeta::core::JSON document =
1174+ sourcemeta::core::parse_json (" {\" foo\" :1,\" bar\" :2,\" baz\" :3}" );
1175+ const auto &object{document.as_object ()};
1176+ sourcemeta::core::JSON::Object::size_type start{10 };
1177+
1178+ const auto hash_foo{object.hash (" foo" )};
1179+ const auto *result{object.try_at (" foo" , hash_foo, start)};
1180+ EXPECT_TRUE (result);
1181+ EXPECT_EQ (result->to_integer (), 1 );
1182+ EXPECT_EQ (start, 1 );
1183+ }
1184+
1185+ TEST (JSON_object, try_at_start_sequential_advances) {
1186+ const sourcemeta::core::JSON document =
1187+ sourcemeta::core::parse_json (" {\" a\" :1,\" b\" :2,\" c\" :3,\" d\" :4}" );
1188+ const auto &object{document.as_object ()};
1189+ sourcemeta::core::JSON::Object::size_type start{0 };
1190+
1191+ const auto hash_a{object.hash (" a" )};
1192+ const auto *result_a{object.try_at (" a" , hash_a, start)};
1193+ EXPECT_TRUE (result_a);
1194+ EXPECT_EQ (result_a->to_integer (), 1 );
1195+
1196+ const auto hash_b{object.hash (" b" )};
1197+ const auto *result_b{object.try_at (" b" , hash_b, start)};
1198+ EXPECT_TRUE (result_b);
1199+ EXPECT_EQ (result_b->to_integer (), 2 );
1200+
1201+ const auto hash_c{object.hash (" c" )};
1202+ const auto *result_c{object.try_at (" c" , hash_c, start)};
1203+ EXPECT_TRUE (result_c);
1204+ EXPECT_EQ (result_c->to_integer (), 3 );
1205+
1206+ const auto hash_d{object.hash (" d" )};
1207+ const auto *result_d{object.try_at (" d" , hash_d, start)};
1208+ EXPECT_TRUE (result_d);
1209+ EXPECT_EQ (result_d->to_integer (), 4 );
1210+
1211+ EXPECT_EQ (start, object.size ());
1212+ }
0 commit comments