Mnesia query: less or equal than given key

Ulf Wiger (AL/EAB) ulf.wiger@REDACTED
Mon Sep 19 17:00:39 CEST 2005


Erik Reitsma wrote:
> 
> Using mnesia, is there an efficient way to find the smallest 
> entry in a table with a key equal to or less than a given key?

It appears as if you intended to write "the _largest_ entry
with a key equal to or less than a given key".


> So suppose that I have keys 10, 23, 33, 34, 56, 100 and I 
> look for 26, I want to get 23 back. If I look for 23, I should get 23.

Here's a first suggestion:

(ord@REDACTED)3> mnesia:create_table(test,[{type, ordered_set}]).
{atomic,ok}
(ord@REDACTED)4> [mnesia:dirty_write({test,N,a}) || N <- [10,23,33,34,56,100]].
[ok,ok,ok,ok,ok,ok]
(ord@REDACTED)5> F = fun(N) -> 
          mnesia:transaction(
             fun() -> 
               case mnesia:read({test,N}) of 
                  [] -> 
                     case mnesia:dirty_prev(test,N) of
                        '$end_of_table' -> [];
                        Prev -> mnesia:read({test,Prev}) 
                     end; [Obj] -> Obj
               end
              end)
          end.
#Fun<erl_eval.6.10732646>
(ord@REDACTED)6> F(26).                                                         {atomic,[{test,23,a}]}                                                          (ord@REDACTED)7> F(23).                                                         {atomic,{test,23,a}}                                                            (ord@REDACTED)8>                                             

It's not 100% safe, since dirty_prev bypasses the 
transaction store, while the second read() doesn't.


/Uffe



More information about the erlang-questions mailing list