Interleave Lists

Steps causing the bug to occur

  1. Interleave two lists of differing lengths, the second list shorter than the second list
  2. See that the last item in the second list is repeated to interleave with the last item(s) of the first list
  3. Repeat but with first list shorter than second list.
  4. This time the last element of the first list is repeated.

Have you found a workaround?

Complicated list counting and truncating operations to ensure that it doesn’t happen, which I can’t get to work consistently. And even then it precludes some use cases. Would be much easier for me if interleave didn’t repeat items at all.

Other notes

  • Vuo version: 2.4.1
  • macOS version: macOS 11
  • CPU: arm64
  • Have you been able to reproduce the problem? Yes, the problem occurs consistently when I follow the steps above
  • How severely does this bug affect you? It prevents me from completing a specific task with Vuo.

It makes the composition of text lists o different length really problematic if you are using lists with dynamic lengths. My example is the Text Expression sub-comp I have made, it works like the QC patch that replaces every instance of a token (say “%@”) with an item from a text or number list. The use of a list to contain the values substituted into my text string is the way to do this in Vuo because Vuo cannot dynamically create input ports, one for each instance of the token string.

text expression.vuo (4.73 KB)

ud.text.flattenListOfTexts.vuo (7.95 KB)

ud.text.textExpression.vuo (4.24 KB)

Screen Shot 2022-04-28 at 1.16.19 pm.png

Screen Shot 2022-04-28 at 1.16.48 pm.png

Screen Shot 2022-04-28 at 1.23.46 pm.png

Perhaps the Interleave Lists node needs a third input as a boolean option to repeat last item in lists or not? I can see where it would be useful to repeat the last item, or cycle through the list again to interleave with a longer list, but in my use case it’s a big problem that I can’t easily work around. Truncating dynamic lists to be the same length isn’t always an obvious function.

 

While an extra menu on the interleave list to rather “Cut to shorter List” as a yes/no boolean sounds great, in the meanwhile below some possible workarounds.

If I’m right, if the shorter list has no empty values, it should be pretty straightforward with 1 node (your first screenshot in the bug report) :

If however the list has empty values, and you need to remove them, Vuo cannot do that easily if I’m right, I’ve posted a node in the node gallery that removes empty values from a list (your second screenshot from the bug report) :

As for your specific example, if you’re able to change the text expression to have the same number of spaces between each parameter, you could use a Process List node.
If I’m right I’m able to output the same text output with 4 nodes instead of your 2 subcompositions (joining the composition).

Hope this helps.

Process List.vuo (4.42 KB)

2 Likes

In my use case I would want every text in the longer list (from splitting the text expression input) to still be used in the Interleave node (even if the value list is empty or shorter). This would be resolved by just inserting empty strings where required i.e. “” in the case of a short list of values to insert.

My problem is I can’t predict if the text expression that is split will have same number of text items as the inserting value list or one more or two more, or even fewer due to user error.

Compare:

Text Epression Split Texts Values to insert
“%@ foo %@” 1 2
“foo: %@ bar” 2 1
“foo: %@ bar %@” 2 2

I look forward to the day I can compile my own C code and do this kind of trivial logical operation in way less time that figuring out complicated ways to make the existing stock of nodes work to do it! A Lua or JS or Python node wouldn’t go astray ;-)  

The stock Haskell interleave function truncates the result to the shorter of the two lists.

ghci> interleave  [1..3] [10..]
[1,10,2,11,3,12]

[10…] is a list comprehension for an infinite length list of integers beginning with 10.

I wrote my own version of interleave to have the behaviour I wanted which is this:

ghci> interleave'  [1..5] [1..5]
[1,1,2,2,3,3,4,4,5,5]
ghci> interleave'  [1..2] [1..5]
[1,1,2,2,3,4,5]
ghci> interleave'  [1..5] [10,20..30]
[1,10,2,20,3,30,4,5]
ghci> interleave'  [1..3] [10,20..70]
[1,10,2,20,3,30,40,50,60,70]

I’d pay for a Haskell node in Vuo! 20 seconds of code to do this and I can use Quicktest on the code in GHCi to be sure it passes any and all unit tests:

interleave' :: [a] -> [a] -> [a]
interleave' (a1:a1s) (a2:a2s) = a1:a2:interleave' a1s a2s
interleave' (a1:a1s) []       = (a1:a1s)
interleave' [] (a2:a2s)       = (a2:a2s)
interleave' _  _              = []  

Uploaded a node in the gallery that may help as I tried to make it output the behaviour of your last comment : Node Set: List : Interleave Lists with Append

The node is as a .c file, so you can look inside if you want to modify it.

But depending on the situation, one would want to block / remove empty list entries. This node outputs a position even if let’s say a text entry is empty.
But there maybe Node Set: List : Block Empty List Values may be helpful.

Capture d’écran 2022-04-29 à 23.58.52.png

You can still achieve that with stock nodes if I’m right.
Compare the Count List Items of the 2 lists, cut the longer list by the amount of items of the shorter list. Then use an append node to append the extra items from the longer list to the interleaved list.
But this involves some nodes.

A - If you know which list can possibly be shorter :

Capture d’écran 2022-04-30 à 11.58.10.png

B - If any list can possibly be shorter :

Capture d’écran 2022-04-30 à 11.56.57.png

Joining the compositions ;)  

A - Same List Possibly Shorter.vuo (4.2 KB)

B - Any List Possibly Shorter.vuo (11.7 KB)

1 Like

@useful_design, maybe it would help if you made a subcomposition that adds empty strings to a list to pad it out to a specified length. With that in hand, if you have list A and list B and want to make list B match the length of list A, then you could use a combination of @Bodysoulspirit’s Cut List method above and your Pad List subcomposition.

A Lua or JS or Python node wouldn’t go astray

With the Execute Shell Command node, you can run scripts written in Python or other languages.

We’re marking this “not a bug” since the Interleave Lists node behaves as described in the documentation.

Thanks for the advice on Execute Shell Command @jstrecker.

Have TeamVuo done any performance testing using python scripts in the Execute Shell Script? I assume the only way to bind data as input and output (to function like any other node in a composition) would be to serialise it into script statements using text processing nodes and then parse the text output from Execute Shell Script into data types as required?