2

I have a string which represents an nD array in the following format:

"[[1, 2, 3, 4, 5], [1, 2, 3, 4, 5], [1, 2, 3, 4, 5], [1, 2, 3, 4, 5]] [[6, 7, 8, 9, 10], [6, 7, 8, 9, 10], [6, 7, 8, 9, 10], [6, 7, 8, 9, 10]] [[11, 12, 13, 14, 15], [11, 12, 13, 14, 15], [11, 12, 13, 14, 15], [11, 12, 13, 14, 15]]"

Now I want to transform this string to a numpy array 4x5x3 (int) (the size could be dynamic based on the number of values within the single and double brackets), something like that:

        /[11, 12, 13, 14, 15]
       / [11, 12, 13, 14, 15]
      /  [11, 12, 13, 14, 15]
     /   [11, 12, 13, 14, 15]    
    /[6, 7, 8, 9, 10]   
   / [6, 7, 8, 9, 10]  
  /  [6, 7, 8, 9, 10] 
 /   [6, 7, 8, 9, 10]                  
[1, 2, 3, 4, 5]   
[1, 2, 3, 4, 5]  
[1, 2, 3, 4, 5] 
[1, 2, 3, 4, 5]

How can this be done efficiently other than looping on every character.

4
  • why is the matrix printed in a slanted fashion, also you are missing some commands in your string representation Commented Jun 26, 2019 at 11:34
  • @DeveshKumarSingh I have it slanted in order to show the depth. The double brackets show the size of the 3rd dimension. Commented Jun 26, 2019 at 11:37
  • Why do you have such a string representation in the first place? eval works fine on standard list displays, it does not work with the numpy array prints. Commented Jun 26, 2019 at 16:08
  • well initially my data are in a different form, however I am applying some merging based on this answer stackoverflow.com/a/50169083 which transforms it to the above format. Commented Jun 26, 2019 at 17:58

1 Answer 1

3

You can simply evaluate the string, transforming it to a tuple of lists of lists. Then convert this to a NumPy array. One trouble is that your string is missing commas after each 2D sub-array (i.e. after ]]). To fix this we just insert these missing commas:

import numpy as np

s = "[[1, 2, 3, 4, 5], [1, 2, 3, 4, 5], [1, 2, 3, 4, 5], [1, 2, 3, 4, 5]] [[6, 7, 8, 9, 10], [6, 7, 8, 9, 10], [6, 7, 8, 9, 10], [6, 7, 8, 9, 10]] [[11, 12, 13, 14, 15], [11, 12, 13, 14, 15], [11, 12, 13, 14, 15], [11, 12, 13, 14, 15]]"
a = np.array(eval(s.replace(']]', ']],')))
print(a)

Note on eval

Using eval is often considered somewhat dangerous, as it can execute arbitrary code. A safer alternative is literal_eval from the ast module:

import ast
a = np.array(ast.literal_eval(s.replace(']]', ']],')))
Sign up to request clarification or add additional context in comments.

2 Comments

good approach. though i'd recommend only suggesting the literal_eval version, and talking about eval only in passing if you must, but not as the main answer.
thanks, that works nice. To be honest I was looking on ast.literal_eval but I am still new in python so couldn't figure out how to use it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.