Browse Source

cJSON_Compare: Fix comparison of objects

It did consider two arrays equal if one is a subset of te other one,
which is incorrect.

See #180
pull/185/head
Max Bruckner 8 years ago
parent
commit
03ba72faec
  1. 19
      cJSON.c
  2. 9
      tests/compare_tests.c

19
cJSON.c

@ -2605,10 +2605,11 @@ CJSON_PUBLIC(cJSON_bool) cJSON_Compare(const cJSON * const a, const cJSON * cons
case cJSON_Object:
{
cJSON *a_element = NULL;
cJSON *b_element = NULL;
cJSON_ArrayForEach(a_element, a)
{
/* TODO This has O(n^2) runtime, which is horrible! */
cJSON *b_element = get_object_item(b, a_element->string, case_sensitive);
b_element = get_object_item(b, a_element->string, case_sensitive);
if (b_element == NULL)
{
return false;
@ -2620,6 +2621,22 @@ CJSON_PUBLIC(cJSON_bool) cJSON_Compare(const cJSON * const a, const cJSON * cons
}
}
/* doing this twice, once on a and b to prevent true comparison if a subset of b
* TODO: Do this the proper way, this is just a fix for now */
cJSON_ArrayForEach(b_element, b)
{
a_element = get_object_item(a, b_element->string, case_sensitive);
if (a_element == NULL)
{
return false;
}
if (!cJSON_Compare(b_element, a_element, case_sensitive))
{
return false;
}
}
return true;
}

9
tests/compare_tests.c

@ -175,6 +175,15 @@ static void cjson_compare_should_compare_objects(void)
"{\"Flse\": false, \"true\": true, \"null\": null, \"number\": 42, \"string\": \"string\", \"array\": [], \"object\": {}}",
"{\"true\": true, \"false\": false, \"null\": null, \"number\": 42, \"string\": \"string\", \"array\": [], \"object\": {}}",
false));
/* test objects that are a subset of each other */
TEST_ASSERT_FALSE(compare_from_string(
"{\"one\": 1, \"two\": 2}",
"{\"one\": 1, \"two\": 2, \"three\": 3}",
true))
TEST_ASSERT_FALSE(compare_from_string(
"{\"one\": 1, \"two\": 2}",
"{\"one\": 1, \"two\": 2, \"three\": 3}",
false))
}
int main(void)

Loading…
Cancel
Save