From: Matthias Clasen Date: Wed, 19 Apr 2006 02:59:37 +0000 (+0000) Subject: Add api to get and set doubles and lists of doubles. (#164719, Maurizio X-Git-Tag: GLIB_2_11_0~36 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=22ec64756c03bb45132b23f6216158fc07a3d21c;p=platform%2Fupstream%2Fglib.git Add api to get and set doubles and lists of doubles. (#164719, Maurizio 2006-04-18 Matthias Clasen * glib/gkeyfile.h: * glib/glib.symbols: * glib/gkeyfile.c: Add api to get and set doubles and lists of doubles. (#164719, Maurizio Monge, Dom Lachowicz) * tests/keyfile-test.c: Add tests for new api. --- diff --git a/ChangeLog b/ChangeLog index f047781..4e34d76 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,12 @@ 2006-04-18 Matthias Clasen + * glib/gkeyfile.h: + * glib/glib.symbols: + * glib/gkeyfile.c: Add api to get and set doubles and + lists of doubles. (#164719, Maurizio Monge, Dom Lachowicz) + + * tests/keyfile-test.c: Add tests for new api. + * glib/gkeyfile.c (g_key_file_add_group): Accept duplicate groups. (#157877, Sebastien Bacher) diff --git a/ChangeLog.pre-2-12 b/ChangeLog.pre-2-12 index f047781..4e34d76 100644 --- a/ChangeLog.pre-2-12 +++ b/ChangeLog.pre-2-12 @@ -1,5 +1,12 @@ 2006-04-18 Matthias Clasen + * glib/gkeyfile.h: + * glib/glib.symbols: + * glib/gkeyfile.c: Add api to get and set doubles and + lists of doubles. (#164719, Maurizio Monge, Dom Lachowicz) + + * tests/keyfile-test.c: Add tests for new api. + * glib/gkeyfile.c (g_key_file_add_group): Accept duplicate groups. (#157877, Sebastien Bacher) diff --git a/docs/reference/ChangeLog b/docs/reference/ChangeLog index e825507..6625048 100644 --- a/docs/reference/ChangeLog +++ b/docs/reference/ChangeLog @@ -1,5 +1,9 @@ 2006-04-18 Matthias Clasen + * glib/glib-sections.txt: Add new keyfile api + +2006-04-18 Matthias Clasen + * gobject/tut_gobject.xml: Say that ref/unref are thread-safe now. (#322883, Christophe Fergeau) diff --git a/docs/reference/glib/glib-sections.txt b/docs/reference/glib/glib-sections.txt index 786b832..cd832ec 100644 --- a/docs/reference/glib/glib-sections.txt +++ b/docs/reference/glib/glib-sections.txt @@ -1464,10 +1464,12 @@ g_key_file_get_string g_key_file_get_locale_string g_key_file_get_boolean g_key_file_get_integer +g_key_file_get_double g_key_file_get_string_list g_key_file_get_locale_string_list g_key_file_get_boolean_list g_key_file_get_integer_list +g_key_file_get_double_list g_key_file_get_comment @@ -1476,10 +1478,12 @@ g_key_file_set_string g_key_file_set_locale_string g_key_file_set_boolean g_key_file_set_integer +g_key_file_set_double g_key_file_set_string_list g_key_file_set_locale_string_list g_key_file_set_boolean_list g_key_file_set_integer_list +g_key_file_set_double_list g_key_file_set_comment g_key_file_remove_group g_key_file_remove_key diff --git a/glib/gkeyfile.c b/glib/gkeyfile.c index eeb8ee1..4456644 100644 --- a/glib/gkeyfile.c +++ b/glib/gkeyfile.c @@ -152,6 +152,9 @@ static gint g_key_file_parse_value_as_integer (GKeyFile GError **error); static gchar *g_key_file_parse_integer_as_value (GKeyFile *key_file, gint value); +static gdouble g_key_file_parse_value_as_double (GKeyFile *key_file, + const gchar *value, + GError **error); static gboolean g_key_file_parse_value_as_boolean (GKeyFile *key_file, const gchar *value, GError **error); @@ -2153,6 +2156,218 @@ g_key_file_set_integer_list (GKeyFile *key_file, g_string_free (values, TRUE); } +/** + * g_key_file_get_double: + * @key_file: a #GKeyFile + * @group_name: a group name + * @key: a key + * @error: return location for a #GError + * + * Returns the value associated with @key under @group_name as an + * integer. If @group_name is %NULL, the start_group is used. + * + * If @key cannot be found then the return value is undefined and + * @error is set to #G_KEY_FILE_ERROR_KEY_NOT_FOUND. Likewise, if + * the value associated with @key cannot be interpreted as a double + * then the return value is also undefined and @error is set to + * #G_KEY_FILE_ERROR_INVALID_VALUE. + * + * Return value: the value associated with the key as a double. + * + * Since: 2.12 + **/ +gdouble +g_key_file_get_double (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + GError **error) +{ + GError *key_file_error; + gchar *value; + gdouble double_value; + + g_return_val_if_fail (key_file != NULL, -1); + g_return_val_if_fail (group_name != NULL, -1); + g_return_val_if_fail (key != NULL, -1); + + key_file_error = NULL; + + value = g_key_file_get_value (key_file, group_name, key, &key_file_error); + + if (key_file_error) + { + g_propagate_error (error, key_file_error); + return 0; + } + + double_value = g_key_file_parse_value_as_double (key_file, value, + &key_file_error); + g_free (value); + + if (key_file_error) + { + if (g_error_matches (key_file_error, + G_KEY_FILE_ERROR, + G_KEY_FILE_ERROR_INVALID_VALUE)) + { + g_set_error (error, G_KEY_FILE_ERROR, + G_KEY_FILE_ERROR_INVALID_VALUE, + _("Key file contains key '%s' in group '%s' " + "which has value that cannot be interpreted."), key, + group_name); + g_error_free (key_file_error); + } + else + g_propagate_error (error, key_file_error); + } + + return double_value; +} + +/** + * g_key_file_set_double: + * @key_file: a #GKeyFile + * @group_name: a group name + * @key: a key + * @value: an double value + * + * Associates a new double value with @key under @group_name. + * If @key cannot be found then it is created. If @group_name + * is %NULL, the start group is used. + * + * Since: 2.12 + **/ +void +g_key_file_set_double (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gdouble value) +{ + gchar result[G_ASCII_DTOSTR_BUF_SIZE]; + + g_return_if_fail (key_file != NULL); + g_return_if_fail (group_name != NULL); + g_return_if_fail (key != NULL); + + g_ascii_dtostr ( result, sizeof (result), value ); + g_key_file_set_value (key_file, group_name, key, result); +} + +/** + * g_key_file_get_double_list: + * @key_file: a #GKeyFile + * @group_name: a group name + * @key: a key + * @length: the number of doubles returned + * @error: return location for a #GError + * + * Returns the values associated with @key under @group_name as + * doubles. If @group_name is %NULL, the start group is used. + * + * If @key cannot be found then the return value is undefined and + * @error is set to #G_KEY_FILE_ERROR_KEY_NOT_FOUND. Likewise, if + * the values associated with @key cannot be interpreted as doubles + * then the return value is also undefined and @error is set to + * #G_KEY_FILE_ERROR_INVALID_VALUE. + * + * Return value: the values associated with the key as a double + * + * Since: 2.12 + **/ +gdouble * +g_key_file_get_double_list (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gsize *length, + GError **error) +{ + GError *key_file_error = NULL; + gchar **values; + gdouble *double_values; + gsize i, num_doubles; + + g_return_val_if_fail (key_file != NULL, NULL); + g_return_val_if_fail (group_name != NULL, NULL); + g_return_val_if_fail (key != NULL, NULL); + + values = g_key_file_get_string_list (key_file, group_name, key, + &num_doubles, &key_file_error); + + if (key_file_error) + g_propagate_error (error, key_file_error); + + if (!values) + return NULL; + + double_values = g_new0 (gdouble, num_doubles); + + for (i = 0; i < num_doubles; i++) + { + double_values[i] = g_key_file_parse_value_as_double (key_file, + values[i], + &key_file_error); + + if (key_file_error) + { + g_propagate_error (error, key_file_error); + g_strfreev (values); + g_free (double_values); + + return NULL; + } + } + g_strfreev (values); + + if (length) + *length = num_doubles; + + return double_values; +} + +/** + * g_key_file_set_double_list: + * @key_file: a #GKeyFile + * @group_name: a group name + * @key: a key + * @list: an array of double values + * @length: number of double values in @list + * + * Associates a list of double values with @key under + * @group_name. If @key cannot be found then it is created. + * If @group_name is %NULL the start group is used. + * + * Since: 2.21 + **/ +void +g_key_file_set_double_list (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gdouble list[], + gsize length) +{ + GString *values; + gsize i; + + g_return_if_fail (key_file != NULL); + g_return_if_fail (group_name != NULL); + g_return_if_fail (key != NULL); + g_return_if_fail (list != NULL); + + values = g_string_sized_new (length * 16); + for (i = 0; i < length; i++) + { + gchar result[G_ASCII_DTOSTR_BUF_SIZE]; + + g_ascii_dtostr( result, sizeof (result), list[i] ); + + g_string_append (values, result); + g_string_append_c (values, ';'); + } + + g_key_file_set_value (key_file, group_name, key, values->str); + g_string_free (values, TRUE); +} + static void g_key_file_set_key_comment (GKeyFile *key_file, const gchar *group_name, @@ -3249,6 +3464,24 @@ g_key_file_parse_integer_as_value (GKeyFile *key_file, return g_strdup_printf ("%d", value); } +static gdouble +g_key_file_parse_value_as_double (GKeyFile *key_file, + const gchar *value, + GError **error) +{ + gchar *end_of_valid_d; + gdouble double_value = 0; + + double_value = g_ascii_strtod (value, &end_of_valid_d); + + if (*end_of_valid_d != '\0') + g_set_error (error, G_KEY_FILE_ERROR, + G_KEY_FILE_ERROR_INVALID_VALUE, + _("Value '%s' cannot be interpreted as a float number."), value); + + return double_value; +} + static gboolean g_key_file_parse_value_as_boolean (GKeyFile *key_file, const gchar *value, diff --git a/glib/gkeyfile.h b/glib/gkeyfile.h index 08c0fe5..8014550 100644 --- a/glib/gkeyfile.h +++ b/glib/gkeyfile.h @@ -126,6 +126,14 @@ void g_key_file_set_integer (GKeyFile *key_file, const gchar *group_name, const gchar *key, gint value); +gdouble g_key_file_get_double (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + GError **error); +void g_key_file_set_double (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gdouble value); gchar **g_key_file_get_string_list (GKeyFile *key_file, const gchar *group_name, const gchar *key, @@ -163,6 +171,16 @@ gint *g_key_file_get_integer_list (GKeyFile *key_file, const gchar *key, gsize *length, GError **error) G_GNUC_MALLOC; +void g_key_file_set_double_list (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gdouble list[], + gsize length); +gdouble *g_key_file_get_double_list (GKeyFile *key_file, + const gchar *group_name, + const gchar *key, + gsize *length, + GError **error) G_GNUC_MALLOC; void g_key_file_set_integer_list (GKeyFile *key_file, const gchar *group_name, const gchar *key, diff --git a/glib/glib.symbols b/glib/glib.symbols index 6c98a3b..2a9a27d 100644 --- a/glib/glib.symbols +++ b/glib/glib.symbols @@ -475,6 +475,8 @@ g_key_file_get_boolean g_key_file_get_boolean_list G_GNUC_MALLOC g_key_file_get_comment G_GNUC_MALLOC g_key_file_get_groups G_GNUC_MALLOC +g_key_file_get_double +g_key_file_get_double_list G_GNUC_MALLOC g_key_file_get_integer g_key_file_get_integer_list G_GNUC_MALLOC g_key_file_get_keys G_GNUC_MALLOC @@ -496,6 +498,8 @@ g_key_file_remove_key g_key_file_set_boolean g_key_file_set_boolean_list g_key_file_set_comment +g_key_file_set_double +g_key_file_set_double_list g_key_file_set_integer g_key_file_set_integer_list g_key_file_set_list_separator diff --git a/tests/keyfile-test.c b/tests/keyfile-test.c index 7680881..e9ec922 100644 --- a/tests/keyfile-test.c +++ b/tests/keyfile-test.c @@ -199,6 +199,49 @@ check_integer_list_value (GKeyFile *keyfile, } static void +check_double_list_value (GKeyFile *keyfile, + const gchar *group, + const gchar *key, + ...) +{ + gint i; + gdouble v, *value; + va_list args; + gsize len; + GError *error = NULL; + + value = g_key_file_get_double_list (keyfile, group, key, &len, &error); + check_no_error (&error); + g_assert (value != NULL); + + va_start (args, key); + i = 0; + v = va_arg (args, gdouble); + while (v != -100) + { + if (i == len) + { + g_print ("Group %s key %s: list too short (%d)\n", + group, key, i); + exit (1); + } + if (value[i] != v) + { + g_print ("Group %s key %s: mismatch at %d, expected %e, got %e\n", + group, key, i, v, value[i]); + exit (1); + } + + i++; + v = va_arg (args, gdouble); + } + + va_end (args); + + g_free (value); +} + +static void check_boolean_list_value (GKeyFile *keyfile, const gchar *group, const gchar *key, @@ -286,6 +329,27 @@ check_integer_value (GKeyFile *keyfile, } static void +check_double_value (GKeyFile *keyfile, + const gchar *group, + const gchar *key, + gdouble expected) +{ + GError *error = NULL; + gdouble value; + + value = g_key_file_get_double (keyfile, group, key, &error); + check_no_error (&error); + + if (value != expected) + { + g_print ("Group %s key %s: " + "expected integer value %e, actual value %e\n", + group, key, expected, value); + exit (1); + } +} + +static void check_name (const gchar *what, const gchar *value, const gchar *expected, @@ -605,9 +669,9 @@ test_boolean (void) g_key_file_free (keyfile); } -/* check parsing of integer values */ +/* check parsing of integer and double values */ static void -test_integer (void) +test_number (void) { GKeyFile *keyfile; GError *error = NULL; @@ -620,6 +684,9 @@ test_integer (void) "key4=2324431\n" "key5=-2324431\n" "key6=000111\n" + "dkey1=000111\n" + "dkey2=145.45\n" + "dkey3=-3453.7\n" "[invalid]\n" "key1=0xffff\n" "key2=0.5\n" @@ -634,6 +701,9 @@ test_integer (void) check_integer_value (keyfile, "valid", "key4", 2324431); check_integer_value (keyfile, "valid", "key5", -2324431); check_integer_value (keyfile, "valid", "key6", 111); + check_double_value (keyfile, "valid", "dkey1", 111.0); + check_double_value (keyfile, "valid", "dkey2", 145.45); + check_double_value (keyfile, "valid", "dkey3", -3453.7); g_key_file_get_integer (keyfile, "invalid", "key1", &error); check_error (&error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_INVALID_VALUE); @@ -727,7 +797,8 @@ test_lists (void) "key5=true;false\n" "key6=1;0;-1\n" "key7= 1 ; 0 ; -1 \n" - "key8=v1\\,v2\n"; + "key8=v1\\,v2\n" + "key9=0;1.3456;-76532.456\n"; keyfile = load_data (data, 0); @@ -737,6 +808,7 @@ test_lists (void) check_string_list_value (keyfile, "valid", "key4", "v1;v2", NULL); check_boolean_list_value (keyfile, "valid", "key5", TRUE, FALSE, -100); check_integer_list_value (keyfile, "valid", "key6", 1, 0, -1, -100); + check_double_list_value (keyfile, "valid", "key9", 0.0, 1.3456, -76532.456, -100.0); /* maybe these should be valid */ /* check_integer_list_value (keyfile, "valid", "key7", 1, 0, -1, -100);*/ /* check_string_list_value (keyfile, "valid", "key8", "v1\\,v2", NULL);*/ @@ -921,7 +993,7 @@ main (int argc, char *argv[]) test_listing (); test_string (); test_boolean (); - test_integer (); + test_number (); test_locale_string (); test_lists (); test_group_remove ();