3
$\begingroup$

I have list of associations like this:

er={<|A->{d11,{"1b1","2b1","3a1"}},B->{d12,{"1a1","2a1","3b1"}},C->{d13,{"1c1","2c1","3c1"}}|>,
<|A->{d21,{"1b2","2b2","3a2"}},B->{d22,{"1a2","2a2","3b2"}},C->{d23,{"1c2","2c2","3c2"}}|>,
<|A->{d31,{"1b3","2b3","3a3"}},B->{d32,{"1a3","2a3","3b3"}},C->{d33,{"1c3","2c3","3c3"}}|>,
<|A->{d41,{"1a4","2a4","3a4"}},B->{d42,{"1b4","2b4","3b4"}},C->{d43,{"1c4","2c4","3c4"}}|>,
<|A->{d51,{"1a5","2a5","3a5"}},B->{d52,{"1b5","2b5","3b5"}},C->{d53,{"1c5","2c5","3c5"}}|>}

I want to swap data between rules A and B and to only on [[2]][[;; 2]]their parts/levels, eg. in A "1b1","2b1" should be "1a1","2a1", and in B "1a1", "2a1" should be "1b1","2b1",...and the same procedure for only next two associations, 3 in total). So, the resulting, corrected list of associations would be:

ok={<|A->{d11,{"1a1","2a1","3a1"}},B->{d12,{"1b1","2b1","3b1"}},C->{d13,{"1c1","2c1","3c1"}}|>,
<|A->{d21,{"1a2","2a2","3a2"}},B->{d22,{"1b2","2b2","3b2"}},C->{d23,{"1c2","2c2","3c2"}}|>,
<|A->{d31,{"1a3","2a3","3a3"}},B->{d32,{"1b3","2b3","3b3"}},C->{d33,{"1c3","2c3","3c3"}}|>,
<|A->{d41,{"1a4","2a4","3a4"}},B->{d42,{"1b4","2b4","3b4"}},C->{d43,{"1c4","2c4","3c4"}}|>,
<|A->{d51,{"1a5","2a5","3a5"}},B->{d52,{"1b5","2b5","3b5"}},C->{d53,{"1c5","2c5","3c5"}}|>}

Please help with composing procedure to rearrange wrong to correct associations.

EDIT: none of the values are fixed and are not known in advance, they are arbitrary numbers. as, bs and cs are used only for exposure and to avoid mess. Only keys (A, B C) are fixed and known in advance.

$\endgroup$
  • 1
    $\begingroup$ You should avoid symbols as key names, and even more capitalized symbols as e.g. C is a built-in symbol. $\endgroup$ – Kuba Feb 28 '18 at 8:02
1
$\begingroup$
Association @* KeyValueMap[
  # -> (
    #2 /. s_String :> StringReplace[s, LetterCharacter :> ToLowerCase[ToString[#]]]
  ) &
] /@ er

enter image description here

$\endgroup$
  • $\begingroup$ this is character replacement, but I want value swapping, because contents of values have NO ties with its keys. eg this {<|A->{d11,{"1yy1","2yy1","3xx1"}}, B->{d12,{"1xx1","2xx1","3yy1"}}, C->{d13,{"1zz1","2zz1","3zz1"}}|>, <|A->{d21,{"1yy2","2yy2","3xx2"}}, B->{d22,{"1xx2","2xx2","3yy2"}}, C->{d23,{"1zz2","2zz2","3zz2"}}|>, <|A->{d41,{"1xx3","2xx3","3xx3"}}, B->{d42,{"1yy3","2yy3","3yy3"}}, C->{d43,{"1zz3","2zz3","3zz3"}}|>, <|A->{d51,{"1xx4","2xx4","3xx4"}}, B->{d52,{"1yy4","2yy4","3yy4"}}, C->{d53,{"1zz4","2zy4","3zz4"}}|>} $\endgroup$ – Dragutin Feb 28 '18 at 8:44
  • $\begingroup$ @Dragutin if there are no ties with A|B|C, how do you know which is swapped and which correct? My answer fits your question, if you have a different question, make sure you explained the problem well. $\endgroup$ – Kuba Feb 28 '18 at 9:53
  • $\begingroup$ swapping is only in first THREE (I determine this number) associations, between A and B keys, on [[2]][[{1,2}]]. so "1yy1","2yy1" swaps with "1xx1","2xx1". All other remain the same. $\endgroup$ – Dragutin Feb 28 '18 at 10:27
  • $\begingroup$ @Dragutin You said "as we can see first 3 associations" and then "none of the values are fixed and are not known in advanced". Your question is not clear, please put some effort and edit it with a clear description what is allowed to happen what not, what part of the structure will not change and what can contain arbitrary expressions. Unless I'm mistaken you are now wasting our time. $\endgroup$ – Kuba Feb 28 '18 at 10:31
0
$\begingroup$

Not the most elegant, but I believe this will do what you want:

Table[
 <|A -> {(A /. er[[i]])[[1]], 
    StringReplace[(A /. er[[i]])[[2]], "b" | "c" -> "a"]},
  B -> {(B /. er[[i]])[[1]], 
    StringReplace[(B /. er[[i]])[[2]], "a" | "c" -> "b"]},
  C -> {(C /. er[[i]])[[1]], 
    StringReplace[(C /. er[[i]])[[2]], "b" | "a" -> "c"]}|>, 
 {i, Length[er]}]

{<|A -> {d11, {"1a1", "2a1", "3a1"}}, 
  B -> {d12, {"1b1", "2b1", "3b1"}}, 
  C -> {d13, {"1c1", "2c1", "3c1"}}|>, <|A -> {d21, {"1a2", "2a2", 
     "3a2"}}, B -> {d22, {"1b2", "2b2", "3b2"}}, 
  C -> {d23, {"1c2", "2c2", "3c2"}}|>, <|A -> {d31, {"1a3", "2a3", 
     "3a3"}}, B -> {d32, {"1b3", "2b3", "3b3"}}, 
  C -> {d33, {"1c3", "2c3", "3c3"}}|>, <|A -> {d41, {"1a4", "2a4", 
     "3a4"}}, B -> {d42, {"1b4", "2b4", "3b4"}}, 
  C -> {d43, {"1c4", "2c4", "3c4"}}|>, <|A -> {d51, {"1a5", "2a5", 
     "3a5"}}, B -> {d52, {"1b5", "2b5", "3b5"}}, 
  C -> {d53, {"1c5", "2c5", "3c5"}}|>}
$\endgroup$
  • $\begingroup$ good idea but in my dataset none of the values are fixed and are not known in advanced, they are arbitrary numbers. Only keys (A, B C) are fixed and known in advance. $\endgroup$ – Dragutin Feb 28 '18 at 7:57
0
$\begingroup$
ok2 = er;
ok2[[;;3]] = ReplaceAll[er[[;;3]], Association[A -> {a_, b_ }, B -> {c_, d_}, rest___] :>
  Association[A -> {a, Append[Most@d, Last@b]}, B-> {c, Append[Most@b, Last@d]}, rest]];
ok2 == ok

True

$\endgroup$
0
$\begingroup$

Thanks for idea. I finally find the solution.

((Association @*({
Keys[#][[1]]->{#[A][[1]],#[B][[2]][[;;2]]~Join~#[A][[2]][[{3}]]},
Keys[#][[2]]->{#[B][[1]],#[A][[2]][[;;2]]~Join~#[B][[2]][[{3}]]},
Keys[#][[3]]->{#[C][[1]],#[C][[2]]}}&)/@#[[;;3]])~Join~#[[4;;]])&@er
$\endgroup$

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.