From 70e2648e02232c1a439a7418388f18fee9afb3fe Mon Sep 17 00:00:00 2001 From: Emmanuele Bassi Date: Sat, 4 Nov 2017 15:43:19 +0000 Subject: [PATCH] Add float comparison utility macros for tests We do compare floating point values elsewhere in our code, so we should ensure that we're doing that with a certain amount of fuzziness. --- json-glib/tests/json-test-utils.h | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 json-glib/tests/json-test-utils.h diff --git a/json-glib/tests/json-test-utils.h b/json-glib/tests/json-test-utils.h new file mode 100644 index 0000000..83a02c6 --- /dev/null +++ b/json-glib/tests/json-test-utils.h @@ -0,0 +1,21 @@ +#include +#include +#include +#include +#include + +#define json_fuzzy_equals(n1,n2,epsilon) \ + (((n1) > (n2) ? ((n1) - (n2)) : ((n2) - (n1))) < (epsilon)) + +#define json_assert_fuzzy_equals(n1,n2,epsilon) \ + G_STMT_START { \ + double __n1 = (n1), __n2 = (n2), __epsilon = (epsilon); \ + if (json_fuzzy_equals (__n1, __n2, __epsilon)) ; else { \ + g_assertion_message_cmpnum (G_LOG_DOMAIN, __FILE__, __LINE__, G_STRFUNC, \ + #n1 " == " #n2 " (+/- " #epsilon ")", \ + __n1, "==", __n2, 'f'); \ + } \ + } G_STMT_END + +#define json_assert_almost_equals(n1,n2) \ + json_assert_fuzzy_equals (n1, n2, DBL_EPSILON) -- 2.17.1 From 675e27505776a1d77fa1ffd1974284890caec1f4 Mon Sep 17 00:00:00 2001 From: Emmanuele Bassi Date: Sat, 4 Nov 2017 15:47:35 +0000 Subject: [PATCH] Use fuzzy comparison for floating point values Direct comparison should never be used for floating point values. Fixes #27 and #28. --- json-glib/tests/array.c | 9 ++------- json-glib/tests/node.c | 16 +++++++--------- json-glib/tests/parser.c | 12 +++--------- json-glib/tests/reader.c | 9 ++------- 4 files changed, 14 insertions(+), 32 deletions(-) diff --git a/json-glib/tests/array.c b/json-glib/tests/array.c index 98afeab..426cd72 100644 --- a/json-glib/tests/array.c +++ b/json-glib/tests/array.c @@ -1,9 +1,4 @@ -#include -#include -#include - -#include -#include +#include "json-test-utils.h" static void test_empty_array (void) @@ -37,7 +32,7 @@ test_add_element (void) json_array_add_double_element (array, 3.14); g_assert_cmpint (json_array_get_length (array), ==, 3); - g_assert_cmpfloat (json_array_get_double_element (array, 2), ==, 3.14); + json_assert_fuzzy_equals (json_array_get_double_element (array, 2), 3.14, 0.001); json_array_add_boolean_element (array, TRUE); g_assert_cmpint (json_array_get_length (array), ==, 4); diff --git a/json-glib/tests/node.c b/json-glib/tests/node.c index 23bda63..80beb78 100644 --- a/json-glib/tests/node.c +++ b/json-glib/tests/node.c @@ -1,6 +1,4 @@ -#include -#include -#include +#include "json-test-utils.h" static void test_init_int (void) @@ -19,7 +17,7 @@ test_init_double (void) JsonNode *node = json_node_new (JSON_NODE_VALUE); json_node_set_double (node, 3.14159); - g_assert_cmpfloat (json_node_get_double (node), ==, 3.14159); + json_assert_fuzzy_equals (json_node_get_double (node), 3.14159, 0.00001); json_node_free (node); } @@ -119,13 +117,13 @@ test_get_int (void) json_node_set_int (node, 0); g_assert_cmpint (json_node_get_int (node), ==, 0); - g_assert_cmpfloat (json_node_get_double (node), ==, 0.0); + json_assert_almost_equals (json_node_get_double (node), 0.0); g_assert (!json_node_get_boolean (node)); g_assert (!json_node_is_null (node)); json_node_set_int (node, 42); g_assert_cmpint (json_node_get_int (node), ==, 42); - g_assert_cmpfloat (json_node_get_double (node), ==, 42.0); + json_assert_almost_equals (json_node_get_double (node), 42.0); g_assert (json_node_get_boolean (node)); g_assert (!json_node_is_null (node)); @@ -138,7 +136,7 @@ test_get_double (void) JsonNode *node = json_node_new (JSON_NODE_VALUE); json_node_set_double (node, 3.14); - g_assert_cmpfloat (json_node_get_double (node), ==, 3.14); + json_assert_fuzzy_equals (json_node_get_double (node), 3.14, 0.001); g_assert_cmpint (json_node_get_int (node), ==, 3); g_assert (json_node_get_boolean (node)); @@ -232,9 +230,9 @@ test_gvalue_autopromotion (void) g_print ("Expecting a gdouble, got a %s\n", g_type_name (G_VALUE_TYPE (&check))); g_assert_cmpint (G_VALUE_TYPE (&check), ==, G_TYPE_DOUBLE); - g_assert_cmpfloat ((float) g_value_get_double (&check), ==, 3.14159f); + json_assert_fuzzy_equals (g_value_get_double (&check), 3.14159, 0.00001); g_assert_cmpint (G_VALUE_TYPE (&value), !=, G_VALUE_TYPE (&check)); - g_assert_cmpfloat ((gdouble) g_value_get_float (&value), ==, g_value_get_double (&check)); + json_assert_almost_equals (g_value_get_float (&value), g_value_get_double (&check)); g_value_unset (&value); g_value_unset (&check); diff --git a/json-glib/tests/parser.c b/json-glib/tests/parser.c index f71584a..8c52a1d 100644 --- a/json-glib/tests/parser.c +++ b/json-glib/tests/parser.c @@ -1,11 +1,5 @@ -#include "config.h" - +#include "json-test-utils.h" #include -#include - -#include - -#include static const gchar *test_empty_string = ""; static const gchar *test_empty_array_string = "[ ]"; @@ -38,13 +32,13 @@ verify_string_value (JsonNode *node) static void verify_double_value (JsonNode *node) { - g_assert_cmpfloat (10.2e3, ==, json_node_get_double (node)); + json_assert_fuzzy_equals (10.2e3, json_node_get_double (node), 0.1); } static void verify_negative_double_value (JsonNode *node) { - g_assert_cmpfloat (-3.14, ==, json_node_get_double (node)); + json_assert_fuzzy_equals (-3.14, json_node_get_double (node), 0.01); } static const struct { diff --git a/json-glib/tests/reader.c b/json-glib/tests/reader.c index 43a6aac..9bab312 100644 --- a/json-glib/tests/reader.c +++ b/json-glib/tests/reader.c @@ -1,9 +1,4 @@ -#include -#include - -#include - -#include +#include "json-test-utils.h" static const gchar *test_base_array_data = "[ 0, true, null, \"foo\", 3.14, [ false ], { \"bar\" : 42 } ]"; @@ -78,7 +73,7 @@ test_base_object (void) g_assert (json_reader_get_error (reader) == NULL); json_reader_read_member (reader, "double"); - g_assert_cmpfloat (json_reader_get_double_value (reader), ==, 42.47); + json_assert_fuzzy_equals (json_reader_get_double_value (reader), 42.47, 0.01); json_reader_end_element (reader); g_object_unref (reader); -- 2.17.1