The Stack Overflow podcast is back! Listen to an interview with our new CEO.

2 added 3 characters in body

Looking at the answer of @happyfish the code below is an overkill...

Here we find the positions corresponding in the values:

pos = Position[vals, _?NumberQ, \[Infinity]]


Here we find the dimensions corresponding to the positions:

posToDims = MapThread[Part, {dims, #}] & /@ pos


Here we make Trie records from the dimensions and the values:

t = MapThread[
Function[{d, p}, Append[d, vals[[Sequence @@ p]]]], {posToDims, pos}, 1]


Here we make the trie:

res = makeTreeAssoc[t]


Finally, we remove the redundant <|{}->{}|> (coming from Shifrin's original implementation):

res /. <|k_ -> <|{} -> {}|>|> :> k

(* {"New York City" -> <|"Terrace house" -> <|"Two bed" -> \
<|"2016" -> 0., "2017" -> 633.25|>,
"Three bed" -> <|"2016" -> 642.96, "2017" -> 677.34|>|>,
"Apartment" -> <|"Two bed" -> <|"2016" -> 591.56,
"2017" -> 632.45|>,
"Three bed" -> <|"2016" -> 634.9, "2017" -> 715.6|>|>|>} *)


## Definitions

Here is a small change of the original definitions are given in this answer:

ClearAll[makeTreeAssoc];
makeTreeAssoc[wrds_ /; MemberQ[wrds, {}]] :=
Prepend[makeTreeAssoc[DeleteCases[wrds, {}]], {} -> {}];
makeTreeAssoc[wrds_] :=
Reap[If[# =!= {}, Sow[Rest[#], First@#]] & /@
wrds, _, #1 -> Association@makeTreeAssoc[#2] &][[2]]


(I was tempted to give an answer with one of my Trie packages, but luckily Leonid Shifrin has provided a concise implementation of Tries using core Association functionalities.)

Looking at the answer of @happyfish the code below is overkill...

Here we find the positions corresponding in the values:

pos = Position[vals, _?NumberQ, \[Infinity]]


Here we find the dimensions corresponding to the positions:

posToDims = MapThread[Part, {dims, #}] & /@ pos


Here we make Trie records from the dimensions and the values:

t = MapThread[
Function[{d, p}, Append[d, vals[[Sequence @@ p]]]], {posToDims, pos}, 1]


Here we make the trie:

res = makeTreeAssoc[t]


Finally, we remove the redundant <|{}->{}|> (coming from Shifrin's original implementation):

res /. <|k_ -> <|{} -> {}|>|> :> k

(* {"New York City" -> <|"Terrace house" -> <|"Two bed" -> \
<|"2016" -> 0., "2017" -> 633.25|>,
"Three bed" -> <|"2016" -> 642.96, "2017" -> 677.34|>|>,
"Apartment" -> <|"Two bed" -> <|"2016" -> 591.56,
"2017" -> 632.45|>,
"Three bed" -> <|"2016" -> 634.9, "2017" -> 715.6|>|>|>} *)


## Definitions

Here is a small change of the original definitions are given in this answer:

ClearAll[makeTreeAssoc];
makeTreeAssoc[wrds_ /; MemberQ[wrds, {}]] :=
Prepend[makeTreeAssoc[DeleteCases[wrds, {}]], {} -> {}];
makeTreeAssoc[wrds_] :=
Reap[If[# =!= {}, Sow[Rest[#], First@#]] & /@
wrds, _, #1 -> Association@makeTreeAssoc[#2] &][[2]]


(I was tempted to give an answer with one of my Trie packages, but luckily Leonid Shifrin has provided a concise implementation of Tries using core Association functionalities.)

Looking at the answer of @happyfish the code below is an overkill...

Here we find the positions corresponding in the values:

pos = Position[vals, _?NumberQ, \[Infinity]]


Here we find the dimensions corresponding to the positions:

posToDims = MapThread[Part, {dims, #}] & /@ pos


Here we make Trie records from the dimensions and the values:

t = MapThread[
Function[{d, p}, Append[d, vals[[Sequence @@ p]]]], {posToDims, pos}, 1]


Here we make the trie:

res = makeTreeAssoc[t]


Finally, we remove the redundant <|{}->{}|> (coming from Shifrin's original implementation):

res /. <|k_ -> <|{} -> {}|>|> :> k

(* {"New York City" -> <|"Terrace house" -> <|"Two bed" -> \
<|"2016" -> 0., "2017" -> 633.25|>,
"Three bed" -> <|"2016" -> 642.96, "2017" -> 677.34|>|>,
"Apartment" -> <|"Two bed" -> <|"2016" -> 591.56,
"2017" -> 632.45|>,
"Three bed" -> <|"2016" -> 634.9, "2017" -> 715.6|>|>|>} *)


## Definitions

Here is a small change of the original definitions are given in this answer:

ClearAll[makeTreeAssoc];
makeTreeAssoc[wrds_ /; MemberQ[wrds, {}]] :=
Prepend[makeTreeAssoc[DeleteCases[wrds, {}]], {} -> {}];
makeTreeAssoc[wrds_] :=
Reap[If[# =!= {}, Sow[Rest[#], First@#]] & /@
wrds, _, #1 -> Association@makeTreeAssoc[#2] &][[2]]


(I was tempted to give an answer with one of my Trie packages, but luckily Leonid Shifrin has provided a concise implementation of Tries using core Association functionalities.)

1

Looking at the answer of @happyfish the code below is overkill...

Here we find the positions corresponding in the values:

pos = Position[vals, _?NumberQ, \[Infinity]]


Here we find the dimensions corresponding to the positions:

posToDims = MapThread[Part, {dims, #}] & /@ pos


Here we make Trie records from the dimensions and the values:

t = MapThread[
Function[{d, p}, Append[d, vals[[Sequence @@ p]]]], {posToDims, pos}, 1]


Here we make the trie:

res = makeTreeAssoc[t]


Finally, we remove the redundant <|{}->{}|> (coming from Shifrin's original implementation):

res /. <|k_ -> <|{} -> {}|>|> :> k

(* {"New York City" -> <|"Terrace house" -> <|"Two bed" -> \
<|"2016" -> 0., "2017" -> 633.25|>,
"Three bed" -> <|"2016" -> 642.96, "2017" -> 677.34|>|>,
"Apartment" -> <|"Two bed" -> <|"2016" -> 591.56,
"2017" -> 632.45|>,
"Three bed" -> <|"2016" -> 634.9, "2017" -> 715.6|>|>|>} *)


## Definitions

Here is a small change of the original definitions are given in this answer:

ClearAll[makeTreeAssoc];
makeTreeAssoc[wrds_ /; MemberQ[wrds, {}]] :=
Prepend[makeTreeAssoc[DeleteCases[wrds, {}]], {} -> {}];
makeTreeAssoc[wrds_] :=
Reap[If[# =!= {}, Sow[Rest[#], First@#]] & /@
wrds, _, #1 -> Association@makeTreeAssoc[#2] &][[2]]


(I was tempted to give an answer with one of my Trie packages, but luckily Leonid Shifrin has provided a concise implementation of Tries using core Association functionalities.)