3
$\begingroup$

I have two lists, one contains the variables and the other the corresponding values that the variables should take.

letters = {"a","m","t","h","e"}
bonus = {10, 20, 30, 40, 50}
words = {math, the, gps, log}

I know that this works (as in the manual of Mathematica):

{a,b,c} = {10,20,30}

But the lists are rather long, so I would like to write:

letters = bonus

Which does not work. Output: I would like to have the variables (letters) taking the values (bonus) a=10, b=20, c=30. Having the weight of the letters, it should be possible to compute the weight of every word in list "words" [math (100), the (120) etc.] I would appreciate some pointers to get me started. Thank you for your time.

$\endgroup$
  • 1
    $\begingroup$ The items in your "letters" List are Strings not Symbols and therefore can't be assigned values. You might be better off creating a Rule for the letter values. $\endgroup$ – Quantum_Oli Mar 12 '16 at 20:28
  • 1
    $\begingroup$ You can try Clear[letters]; Evaluate@(Symbol /@ letters) = bonus. This will create symbols from your strings, then assign them a value, i.e. a=10 etc. Beware that the Clear bit is important if you plan to run this code more than once. Notice, however, that you are NOT assigning a value TO THE STRING "a", but to the symbol a. This may still not work for what you want. An Association construct would probably work a lot better. $\endgroup$ – MarcoB Mar 12 '16 at 20:31
  • $\begingroup$ @Xavier, @Quantum_Oli, @garej - I used "// Timing" to time the processes. The three answers below demand different times with a dictionary of about 240 thousand words. Plus: 0.005087, Total: 0.013299 and Map: 0.039653. The Plus solution is thus the quickest. $\endgroup$ – JSP Mar 14 '16 at 15:48
5
$\begingroup$

Using associations:

letters = {"a","m","t","h","e"};
bonus = {10, 20, 30, 40, 50};
words = {math, the, gps, log};

assoc = AssociationThread[letters -> bonus];

Plus @@@ (Lookup[assoc, #, 0] & /@ Characters[ToString /@ words])

(* {100, 120, 0, 0} *)

If the words are strings, rather than symbols, then simply Characters[words] instead of Characters[ToString /@ words].

$\endgroup$
  • $\begingroup$ Sorry for the delay before responding, I have been travelling. Thank you @Xavier, It works like a charm. I have to understand Associations. Every time I get here I learn something. $\endgroup$ – JSP Mar 14 '16 at 15:11
  • $\begingroup$ Re: associations -- You may find this post (52393) useful. $\endgroup$ – user31159 Mar 14 '16 at 15:29
3
$\begingroup$

Converting your words to strings first:

    letters = {"a", "m", "t", "h", "e"}
    bonus = {10, 20, 30, 40, 50}
    words = {"math", "the", "gps", "log"}

We can create a list of rules for the values of letters (rather than assign values to many variables):

    Thread[letters -> bonus]

{"a" -> 10, "m" -> 20, "t" -> 30, "h" -> 40, "e" -> 50}

Then we can use Characters to split each word into a list of it's characters:

    Characters /@ words

{{"m", "a", "t", "h"}, {"t", "h", "e"}, {"g", "p", "s"}, {"l", "o", "g"}}

Putting it all together:

    Total /@ ((Characters /@ words) /. Thread[letters -> bonus])

{100, 120, "g" + "p" + "s", "g" + "l" + "o"}

$\endgroup$
  • $\begingroup$ Sorry for the delay before responding, I have been travelling. Thank you @Quantum_Oli, It works like a charm. Every time I get here I learn something. It is especially useful with such a pedagogical explanation! $\endgroup$ – JSP Mar 14 '16 at 15:15
2
$\begingroup$
letters = {"a", "m", "t", "h", "e"};
bonus = {10, 20, 30, 40, 50};
words = {math, the, gps, log};

Solution:

Map[Total @ Replace[#, Append[Thread[letters -> bonus], _ -> 0], 1] &,
Characters[ToString /@ words]]

{100, 120, 0, 0}

$\endgroup$
  • $\begingroup$ Thank you @garey, it also works nicely. I will try to find the timings for all three solutions (if I can do that). I do not understand the "_->0". Where can I read about it? Thanks. $\endgroup$ – JSP Mar 14 '16 at 15:23
  • $\begingroup$ @JSP, This is a pattern with Rule. You may see that Raplace expects a pattern as an option. So your letter->score are simple replacement rules that applied first. Then _->0 construct applies (it replaces all the rest letters in characters list). It means "replace any symbol to 0". Here _ is blank and stands for any symbol. $\endgroup$ – garej Mar 14 '16 at 15:31

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.