couchdb-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From rnew...@apache.org
Subject [2/4] ets-lru commit: updated refs/heads/windsor-merge to e9a75fb
Date Fri, 01 Aug 2014 09:08:18 GMT
Add new match and match_object functions


Project: http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/repo
Commit: http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/commit/807c21ad
Tree: http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/tree/807c21ad
Diff: http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/diff/807c21ad

Branch: refs/heads/windsor-merge
Commit: 807c21ad4b7236b0c029b0a608ad2bce6a65785d
Parents: cd8777b
Author: Brian Mitchell <brian@cloudant.com>
Authored: Tue Oct 15 10:04:09 2013 -0400
Committer: Robert Newson <rnewson@apache.org>
Committed: Mon Jul 28 17:21:28 2014 +0100

----------------------------------------------------------------------
 src/ets_lru.erl | 33 +++++++++++++++++++++++++++++++++
 test/06-match.t | 44 ++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 77 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/blob/807c21ad/src/ets_lru.erl
----------------------------------------------------------------------
diff --git a/src/ets_lru.erl b/src/ets_lru.erl
index dc68fb8..7311081 100644
--- a/src/ets_lru.erl
+++ b/src/ets_lru.erl
@@ -20,6 +20,8 @@
 
     insert/3,
     lookup/2,
+    match/3,
+    match_object/3,
     remove/2,
     clear/1,
 
@@ -78,6 +80,23 @@ insert(LRU, Key, Val) ->
 remove(LRU, Key) ->
     gen_server:call(LRU, {remove, Key}).
 
+%% @doc match/3 provides an efficient way to retrieve parts of the
+%% keys and values without copying or requiring circumvention of the
+%% ets_lru API. The KeySpec and ValueSpec parameters are used as part
+%% of one larger match spec so keep in mind that all capturing
+%% placeholders will be aliased between the key and value parts.
+-spec match(atom() | pid(), term(), term()) -> [[any()]].
+match(LRU, KeySpec, ValueSpec) ->
+    gen_server:call(LRU, {match, KeySpec, ValueSpec}).
+
+%% @doc match_object/3 provides an efficient way to retrieve multiple
+%% values using match conditions. The KeySpec and ValueSpec parameters
+%% are used as part of one larger match spec so keep in mind that all
+%% capturing placeholders will be aliased between the key and value
+%% parts.
+-spec match_object(atom() | pid(), term(), term()) -> [any()].
+match_object(LRU, KeySpec, ValueSpec) ->
+    gen_server:call(LRU, {match_object, KeySpec, ValueSpec}).
 
 clear(LRU) ->
     gen_server:call(LRU, clear).
@@ -122,6 +141,20 @@ handle_call({lookup, Key}, _From, St) ->
     end,
     {reply, Reply, St, 0};
 
+handle_call({match_object, KeySpec, ValueSpec}, _From, St) ->
+    Pattern = #entry{key=KeySpec, val=ValueSpec, _='_'},
+    Entries = ets:match_object(St#st.objects, Pattern),
+    Values = lists:map(fun(#entry{key=Key,val=Val}) ->
+        accessed(Key, St),
+        Val
+    end, Entries),
+    {reply, Values, St, 0};
+
+handle_call({match, KeySpec, ValueSpec}, _From, St) ->
+    Pattern = #entry{key=KeySpec, val=ValueSpec, _='_'},
+    Values = ets:match(St#st.objects, Pattern),
+    {reply, Values, St, 0};
+
 handle_call({insert, Key, Val}, _From, St) ->
     NewATime = erlang:now(),
     Pattern = #entry{key=Key, atime='$1', _='_'},

http://git-wip-us.apache.org/repos/asf/couchdb-ets-lru/blob/807c21ad/test/06-match.t
----------------------------------------------------------------------
diff --git a/test/06-match.t b/test/06-match.t
new file mode 100644
index 0000000..907ae78
--- /dev/null
+++ b/test/06-match.t
@@ -0,0 +1,44 @@
+#!/usr/bin/env escript
+
+-define(WITH_LRU(F), tutil:with_lru(fun(LRU) -> F(LRU) end)).
+
+main([]) ->
+    code:add_pathz("test"),
+    code:add_pathz("ebin"),
+    tutil:run(6, fun() -> test() end).
+
+test() ->
+    ?WITH_LRU(test_match_zero_values),
+    ?WITH_LRU(test_match_one_value),
+    ?WITH_LRU(test_match_many_values),
+    ?WITH_LRU(test_match_zero_objects),
+    ?WITH_LRU(test_match_one_object),
+    ?WITH_LRU(test_match_many_objects),
+    ok.
+
+test_match_zero_values(LRU) ->
+    etap:is(ets_lru:match(LRU, a, '$1'), [], "Empty match").
+
+test_match_one_value(LRU) ->
+    ets_lru:insert(LRU, b, {x,y}),
+    Values = ets_lru:match(LRU, b, {'$1', '$2'}),
+    etap:is(Values, [[x,y]], "Single match").
+
+test_match_many_values(LRU) ->
+    ets_lru:insert(LRU, boston, {state, "MA"}),
+    ets_lru:insert(LRU, new_york, {state, "NY"}),
+    Values = ets_lru:match(LRU, '_', {state, '$1'}),
+    etap:is(lists:sort(Values), [["MA"],["NY"]], "Multiple match").
+
+test_match_zero_objects(LRU) ->
+    etap:is(ets_lru:match_object(LRU, a, '$1'), [], "Empty match_object").
+
+test_match_one_object(LRU) ->
+    ets_lru:insert(LRU, ans, 42),
+    etap:is(ets_lru:match_object(LRU, ans, '$1'), [42], "Single match_object").
+
+test_match_many_objects(LRU) ->
+    ets_lru:insert(LRU, {color, blue}, a),
+    ets_lru:insert(LRU, {color, red}, b),
+    Values = ets_lru:match_object(LRU, {color, '_'}, '_'),
+    etap:is(lists:sort(Values), [a, b], "Multiple match_object").


Mime
View raw message