diff options
author | Sverker Eriksson <[email protected]> | 2014-03-12 20:11:10 +0100 |
---|---|---|
committer | Sverker Eriksson <[email protected]> | 2014-03-14 15:08:23 +0100 |
commit | c543d5bff7fb23c3f44cc4817c0654117de78919 (patch) | |
tree | 2ef05bcb7ea4a167b69a2938009fe25a137cc6aa /lib | |
parent | 8fbe76d64e7d55eb41943484602b928658313a65 (diff) | |
download | otp-c543d5bff7fb23c3f44cc4817c0654117de78919.tar.gz otp-c543d5bff7fb23c3f44cc4817c0654117de78919.tar.bz2 otp-c543d5bff7fb23c3f44cc4817c0654117de78919.zip |
erts: Change external format for maps
to be: 116,Arity, K1,V1,K2,V2,...,Kn,Vn
instead of: 116,Arity, K1,K2,...,Kn, V1,V2,....,Vn
We think this will be better for future internal map structures
like HAMT. Would be bad if we need to iterate twice over HAMT
in term_to_binary, one for keys and one for values.
Diffstat (limited to 'lib')
5 files changed, 20 insertions, 24 deletions
diff --git a/lib/debugger/test/map_SUITE.erl b/lib/debugger/test/map_SUITE.erl index e9f4ea1fad..741ad2dc41 100644 --- a/lib/debugger/test/map_SUITE.erl +++ b/lib/debugger/test/map_SUITE.erl @@ -790,16 +790,16 @@ t_map_encode_decode(Config) when is_list(Config) -> %% literally #{ b=>2, a=>1 } in the internal order #{ a:=1, b:=2 } = - erlang:binary_to_term(<<131,116,0,0,0,2,100,0,1,98,100,0,1,97,97,2,97,1>>), + erlang:binary_to_term(<<131,116,0,0,0,2,100,0,1,98,97,2,100,0,1,97,97,1>>), %% literally #{ "hi" => "value", a=>33, b=>55 } in the internal order #{ a:=33, b:=55, "hi" := "value"} = erlang:binary_to_term(<<131,116,0,0,0,3, 107,0,2,104,105, % "hi" :: list() - 100,0,1,97, % a :: atom() - 100,0,1,98, % b :: atom() 107,0,5,118,97,108,117,101, % "value" :: list() + 100,0,1,97, % a :: atom() 97,33, % 33 :: integer() + 100,0,1,98, % b :: atom() 97,55 % 55 :: integer() >>), @@ -829,7 +829,8 @@ map_encode_decode_and_match([{K,V}|Pairs], EncodedPairs, M0) -> B0 = erlang:term_to_binary(M1), Ls = lists:sort(fun(A,B) -> erts_internal:cmp_term(A,B) < 0 end, [{K, erlang:term_to_binary(K), erlang:term_to_binary(V)}|EncodedPairs]), %% sort Ks and Vs according to term spec, then match it - ok = match_encoded_map(B0, length(Ls), [Kbin||{_,Kbin,_}<-Ls] ++ [Vbin||{_,_,Vbin}<-Ls]), + KVbins = lists:foldr(fun({_,Kbin,Vbin}, Acc) -> [Kbin,Vbin | Acc] end, [], Ls), + ok = match_encoded_map(B0, length(Ls), KVbins), %% decode and match it M1 = erlang:binary_to_term(B0), map_encode_decode_and_match(Pairs,Ls,M1); diff --git a/lib/erl_interface/doc/src/ei.xml b/lib/erl_interface/doc/src/ei.xml index 1756ee8a7d..90495eebd6 100644 --- a/lib/erl_interface/doc/src/ei.xml +++ b/lib/erl_interface/doc/src/ei.xml @@ -422,19 +422,18 @@ ei_x_encode_empty_list(&x); <fsummary>Encode a map</fsummary> <desc> <p>This function encodes a map header, with a specified arity. The next - <c>arity</c> terms encoded will be the keys of the map, and the next - <c>arity</c> terms after that will be the corresponding values in - same order.</p> + <c>arity*2</c> terms encoded will be the keys and values of the map + encoded in the following order: <c>K1, V1, K2, V2, ..., Kn, Vn</c>. + </p> <p>E.g. to encode the map <c>#{a => "Apple", b => "Banana"}</c>:</p> <pre> ei_x_encode_map_header(&x, 2); ei_x_encode_atom(&x, "a"); -ei_x_encode_atom(&x, "b"); ei_x_encode_string(&x, "Apple"); +ei_x_encode_atom(&x, "b"); ei_x_encode_string(&x, "Banana"); </pre> - <p>A correctly encoded map can not have duplicate keys, but no check - for duplicate keys is done by this function.</p> + <p>A correctly encoded map can not have duplicate keys.</p> </desc> </func> <func> @@ -664,10 +663,9 @@ ei_x_encode_string(&x, "Banana"); <desc> <p>This function decodes a map header from the binary format. The number of key-value pairs is returned in - <c>arity</c>. Keys and values follows, first all keys and then all values, - which makes a total of <c>arity*2</c> terms. - Keys and values are paired according to their order, the first key - with the first value and so on. If <c>arity</c> is zero, it's an empty map. + <c>*arity</c>. Keys and values follow in the following order: + <c>K1, V1, K2, V2, ..., Kn, Vn</c>. This makes a total of + <c>arity*2</c> terms. If <c>arity</c> is zero, it's an empty map. A correctly encoded map does not have duplicate keys.</p> </desc> </func> diff --git a/lib/erl_interface/test/ei_decode_encode_SUITE_data/ei_decode_encode_test.c b/lib/erl_interface/test/ei_decode_encode_SUITE_data/ei_decode_encode_test.c index 790d498a1d..fcf546105b 100644 --- a/lib/erl_interface/test/ei_decode_encode_SUITE_data/ei_decode_encode_test.c +++ b/lib/erl_interface/test/ei_decode_encode_SUITE_data/ei_decode_encode_test.c @@ -527,8 +527,9 @@ TESTCASE(test_ei_decode_encode) { /* #{atom => atom, atom => pid, port => ref }*/ struct Type* map[] = { &map_type, - &my_atom_type, &my_atom_type, &port_type, - &my_atom_type, &pid_type, &ref_type + &my_atom_type, &my_atom_type, + &my_atom_type, &pid_type, + &port_type, &ref_type }; decode_encode(map, 7); } diff --git a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpErlangMap.java b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpErlangMap.java index 7c1cf84e98..03c18e55a2 100644 --- a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpErlangMap.java +++ b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpErlangMap.java @@ -125,8 +125,6 @@ public class OtpErlangMap extends OtpErlangObject implements Serializable, for (int i = 0; i < arity; i++) { keys[i] = buf.read_any(); - } - for (int i = 0; i < arity; i++) { values[i] = buf.read_any(); } } else { @@ -227,8 +225,6 @@ public class OtpErlangMap extends OtpErlangObject implements Serializable, for (int i = 0; i < arity; i++) { buf.write_any(keys[i]); - } - for (int i = 0; i < arity; i++) { buf.write_any(values[i]); } } diff --git a/lib/jinterface/test/jinterface_SUITE_data/Maps.java b/lib/jinterface/test/jinterface_SUITE_data/Maps.java index 136a665f23..653defc621 100644 --- a/lib/jinterface/test/jinterface_SUITE_data/Maps.java +++ b/lib/jinterface/test/jinterface_SUITE_data/Maps.java @@ -42,16 +42,16 @@ class Maps { runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 1, 100, 0, 1, 97, 100, 0, 1, 98 }, "#{a => b}", 2); // make sure keys are sorted here, jinterface doesn't reorder them - runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 100, 0, 1, 97, - 106, 97, 1 }, "#{2 => [],a => 1}", 3); + runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 106, + 100, 0, 1, 97, 97, 1 }, "#{2 => [],a => 1}", 3); runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 1, 104, 1, 97, 3, 108, 0, 0, 0, 1, 100, 0, 1, 114, 106 }, "#{{3} => [r]}", 4); try { // #{2 => [],a => 1} final OtpErlangMap map = new OtpErlangMap(new OtpInputStream( - new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 100, 0, 1, - 97, 106, 97, 1 })); + new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 106, + 100, 0, 1, 97, 97, 1 })); if (map.arity() != 2) { fail(5); |