Take the 2-minute tour ×
Mathematica Stack Exchange is a question and answer site for users of Mathematica. It's 100% free, no registration required.

I want to replace the values of 1. in slot under the condition that the year and month in basevalue and slot have to be matched

Here are my matrices:

basevalue = {{{2012, 9}, 0.2819}, {{2012, 10}, 1.01406}, {{2012, 11}, 1.06447}, {{2012, 12}, 0.929704}, {{2013, 1}, 1.11471}, {{2013, 2}, 1.08585}}

slot = {{{2012, 3}, 1.}, {{2012, 4}, 1.}, {{2012, 5}, 1.}, {{2012, 6}, 1.}, {{2012, 7}, 1.}, {{2012, 8}, 1.}, {{2012, 9}, 1.}, {{2012, 10}, 1.}, {{2012, 11}, 1.}, {{2012, 12}, 1.}, {{2013, 1}, 1.}, {{2013, 2}, 1.}}

I have tried the following code by my own

Map[Function[arg, ReplacePart[arg, 2 -> Select[basevalue, #[[1]] == arg[[1]] &][[All, -1]] ]], slot] , but it returned me different from what I want.

I think I still do not fully understand how to use function :(

Any helps or suggestions would be appreciated

Thank you

share|improve this question

2 Answers 2

up vote 2 down vote accepted
newslot=Replace[slot, 
 Rule @@@ Cases[GatherBy[Join[slot, basevalue], First], {_, _}], 1]

If you want only those in the slot list with a 1. "blank" to be replaced (i.e., if there can be members of slot that have a matching date in the basevalue list, but not a 1. in the "blank" position), use:

Replace[slot, 
 Rule @@@ Cases[GatherBy[Join[Cases[slot, {_, 1.}], basevalue], First], {_, _}], 1]

and a sneaky way that is probably faster for large lists (assuming you want sort by date and with caveat re: comments):

Sort[DeleteDuplicates[Join[basevalue, slot], #2[[1]] == #1[[1]] &]]

and as long as the slot/basevalue follow some basic rules, a goofy-fast solution:

Transpose[{slot[[All, 1]], Extract[SparseArray[Join[Rule @@@ basevalue, Rule @@@ slot]], 
   slot[[All, 1]]]}]

for the terse fans:

slot /. ({#[[1]], 1.} -> # & /@ basevalue)
share|improve this answer
    
I think the second code returns differently from the first one if you have more period (month) in basevalue than slot. –  newbie Mar 4 at 4:43
    
@newbie: Of course. If you have a replacement list that has "keys" not a subset of the target, that method is a no-go. I assumed from OP that replacements are for some existing set. Added caveat to answer... –  rasher Mar 4 at 4:50
    
Thank you very much for your help. If I understand correctly the first one is more strict since Cases only picks the one that existing in basevalue. –  newbie Mar 4 at 4:53
    
@newbie: yes, the first is the most general (or strict, depending on your semantics): it will only replace entries in the slots that exist in basvalues. Your post implies the target has 1. as the "blank", if that's not always the case, might want to say so in your OP, since these methods assume basically that (i.e., if the "date" matches in the target, replace the "blank" (1.) with a new value). –  rasher Mar 4 at 4:58
    
@newbie: I want to be sure my answer is responsive to your question. If not, I'll happily jigger it or delete it. If an answer does fit your needs, you can mark it or comment as such. I didn't think the question ambiguous, but I'm wondering if I misinterpreted it. –  rasher Mar 4 at 6:01

Just for variety:

Module[{w},
 SortBy[Last@
   Reap[Sow[#2, w[#1]] & @@@ Join[basevalue, slot], _, 
    First /@ {#1, #2} &], First]]

yields:

{{{2012, 3}, 1.}, {{2012, 4}, 1.}, {{2012, 5}, 1.}, {{2012, 6}, 
  1.}, {{2012, 7}, 1.}, {{2012, 8}, 1.}, {{2012, 9}, 
  0.2819}, {{2012, 10}, 1.01406}, {{2012, 11}, 1.06447}, {{2012, 12}, 
  0.929704}, {{2013, 1}, 1.11471}, {{2013, 2}, 1.08585}}
share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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