diff --git a/doc/apiref.rst b/doc/apiref.rst index 9f6a67d..198c0c2 100644 --- a/doc/apiref.rst +++ b/doc/apiref.rst @@ -505,6 +505,35 @@ A JSON array is an ordered collection of other JSON values. Appends all elements in *other_array* to the end of *array*. Returns 0 on success and -1 on error. +The following macro can be used to iterate through all elements +in an array. + +.. function:: json_array_foreach(array, index, value) + + Iterate over every element of ``array``, running the block + of code that follows each time with the proper values set to + variables ``index`` and ``value``, of types :type:`int` and + :type:`json_t *` respectively. Example:: + + /* array is a JSON array */ + size_t index; + json_t *value; + + json_array_foreach(array, index, value) { + /* block of code that uses index and value */ + } + + The items are returned in increasing index order. + + This macro expands to an ordinary ``for`` statement upon + preprocessing, so its performance is equivalent to that of + hand-written code using the array access functions. + The main advantage of this macro is that it abstracts + away the complexity, and makes for shorter, more + concise code. + + .. versionadded:: 2.5 + Object ====== diff --git a/src/jansson.h b/src/jansson.h index e53a301..6bbc0cb 100644 --- a/src/jansson.h +++ b/src/jansson.h @@ -148,6 +148,11 @@ int json_object_iter_set_new(json_t *object, void *iter, json_t *value); key && (value = json_object_iter_value(json_object_key_to_iter(key))); \ key = json_object_iter_key(json_object_iter_next(object, json_object_key_to_iter(key)))) +#define json_array_foreach(array, index, value) \ + for(index = 0; \ + index < json_array_size(array) && (value = json_array_get(array, index)); \ + index++) + static JSON_INLINE int json_object_set(json_t *object, const char *key, json_t *value) { diff --git a/test/suites/api/test_array.c b/test/suites/api/test_array.c index cb273f8..51d47ed 100644 --- a/test/suites/api/test_array.c +++ b/test/suites/api/test_array.c @@ -400,6 +400,25 @@ static void test_circular() json_decref(array1); } +static void test_array_foreach() +{ + size_t index; + json_t *array1, *array2, *value; + + array1 = json_pack("[sisisi]", "foo", 1, "bar", 2, "baz", 3); + array2 = json_array(); + + json_array_foreach(array1, index, value) { + json_array_append(array2, value); + } + + if(!json_equal(array1, array2)) + fail("json_array_foreach failed to iterate all elements"); + + json_decref(array1); + json_decref(array2); +} + static void run_tests() { @@ -409,4 +428,5 @@ static void run_tests() test_clear(); test_extend(); test_circular(); + test_array_foreach(); } diff --git a/test/suites/api/test_object.c b/test/suites/api/test_object.c index 31cadc3..8f6bf8a 100644 --- a/test/suites/api/test_object.c +++ b/test/suites/api/test_object.c @@ -479,7 +479,7 @@ static void test_preserve_order() json_decref(object); } -static void test_foreach() +static void test_object_foreach() { const char *key; json_t *object1, *object2, *value; @@ -507,5 +507,5 @@ static void run_tests() test_set_nocheck(); test_iterators(); test_preserve_order(); - test_foreach(); + test_object_foreach(); }