[erlang-questions] QLC question

Ulf Wiger <>
Mon May 2 22:11:51 CEST 2011


If you have a record within a record, you can simply use pattern matching:

1> rd(data, {id, nick}).
data
2> rd(wrapper, {id, data}).
wrapper

3> L = [#wrapper{id=1,data=#data{id=1}}, #wrapper{id=2,data=#data{id=2,nick=n}}].
[#wrapper{id = 1,data = #data{id = 1,nick = undefined}},
 #wrapper{id = 2,data = #data{id = 2,nick = n}}]

4> qlc:e(qlc:q([W || #wrapper{data = #data{nick = N}} = W <- L, N =/= undefined])).
[#wrapper{id = 2,data = #data{id = 2,nick = n}}]

If this becomes to hairy, you can use a guard function which does deep inspection on the record. In LCs, a guard function can be any Erlang function.

A generator in QLC must either be a list, or a special QLC generator (e.g. what you get as a return value from qlc:q/1 or mnesia:table/1). In this particular case, QLC seems to complain already in the query analysis stage, as it doesn't like the fact that a dynamic variable is assumed to be a valid generator.

BR,
Ulf W

On 2 May 2011, at 21:50, Chris Hicks wrote:

> I've got a record nested within a record like this:
> 
> {account_wrapper, "Username", {account_data, ...}}
> 
> And what I want to do is use QLC to search that inner record and see if someone already has chosen a nickname for an account during registration. However, since I've never used QLC before I wanted to start out slow and just get a feel, creating more complex QLC's as I went along until I got where I wanted to go. First I tried this:
> 
> mnesia:activity(transaction, fun() -> qlc:eval(qlc:q([{A, B, C} || Wrapper <- mnesia:table(accounts), {A, B, C} <- Wrapper])) end, []).
> 
> I just wanted to make sure I understood how to unpack data structures...however I keep getting a qlc error:
> 
> ** exception exit: {aborted,{badarg,[{qlc,eval,
>                                           [{error,qlc,
>                                                   {1,qlc,{used_generator_variable,'Wrapper'}}},
>                                            []]},
>                                      {mnesia_tm,apply_fun,3},
>                                      {mnesia_tm,execute_transaction,5},
>                                      {mnesia,wrap_trans,6},
>                                      {erl_eval,do_apply,5},
>                                      {shell,exprs,7},
>                                      {shell,eval_exprs,7},
>                                      {shell,eval_loop,3}]}}
>      in function  mnesia:wrap_trans/6
> 
> 
> Now from everything I've read...I thought I'd be able to use the Wrapper variable later on in the query as a generator...thus allowing me to unpack things. Why would this be giving me an error? If I change it to:
> 
> mnesia:activity(transaction, fun() -> qlc:eval(qlc:q([{A, B, C} || {A, B, C} <- mnesia:table(accounts)])) end, []).
> 
> It works just fine and returns the record...and I can successfully match the pattern {A, B, C} with the account_wrapper record elsewhere. So what am I missing?
> 
> Chris Hicks.
> 
> _______________________________________________
> erlang-questions mailing list
> 
> http://erlang.org/mailman/listinfo/erlang-questions

Ulf Wiger, CTO, Erlang Solutions, Ltd.
http://erlang-solutions.com



-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20110502/0abf96fb/attachment.html>


More information about the erlang-questions mailing list