How to gather data in my case using gather_nd in tensorflow? - python

I need to gather some data from Tensor, I used gather_nd. Now code is above
import tensorflow as tf
indices = [[[0, 4], [0, 1], [0, 6], [0, 2]],
[[1, 1], [1, 4], [1, 0], [1, 9]],
[[2, 5], [2, 1], [2, 9], [2, 6]]]
params = [[4,6,3,6,7,8,4,5,3,8], [9,5,6,2,6,5,1,9,6,4], [4,6,6,1,3,2,6,7,1,8]]
output = tf.gather_nd(params, indices)
sess = tf.Session()
print sess.run(output)
The output is
[[7 6 4 3]
[5 6 9 4]
[2 6 8 6]]
Yep, that's what I want. I want to take out the values located at 4,1,6,2 in params[0]. They are 7, 6, 4, 3 because params[0][4] = 7, params[0][1] = 6, params[0][6] = 4, params[0][2] = 3.
However, tf.gather_nd only receives a indices like above. Now my raw_indices is like,
[[4, 1, 6, 2],
[1, 4, 0, 9],
[5, 1, 9, 6]]
How can I transfer the raw_indices to indices in tensorflow? Yes, I have to do this step in tensor graph since raw_indices is generated in the middle of the graph.

A mixture of tf.range() and some tiling seems to work:
def index_matrix_to_pairs(index_matrix):
replicated_first_indices = tf.tile(
tf.expand_dims(tf.range(tf.shape(index_matrix)[0]), dim=1),
[1, tf.shape(index_matrix)[1]])
return tf.pack([replicated_first_indices, index_matrix], axis=2)
start = [[4, 1, 6, 2],
[1, 4, 0, 9],
[5, 1, 9, 6]]
with tf.Session():
print(index_matrix_to_pairs(start).eval())
Gives:
[[[0 4]
[0 1]
[0 6]
[0 2]]
[[1 1]
[1 4]
[1 0]
[1 9]]
[[2 5]
[2 1]
[2 9]
[2 6]]]
It's just generating the first part of each pair with a tiled tf.range() op, then packing that with the specified indices.

Related

Convert one-dimensional array to two-dimensional array so that each element is a row in the result

I want to know how to convert this: array([0, 1, 2, 3, 4, 5]) to this:
array([[0, 0, 0],
[1, 1, 1],
[2, 2, 2],
[3, 3, 3],
[4, 4, 4],
[5, 5, 5]])
In short, given a flat array, repeat each element inside the array n times, so that each element creates a sub-array of n of the same element, and concatenate these sub-arrays into one, so that each row contains an element from the original array repeated n times.
I can do this:
def repeat(lst, n):
return [[e]*n for e in lst]
>repeat(range(10), 4)
[[0, 0, 0, 0],
[1, 1, 1, 1],
[2, 2, 2, 2],
[3, 3, 3, 3],
[4, 4, 4, 4],
[5, 5, 5, 5],
[6, 6, 6, 6],
[7, 7, 7, 7],
[8, 8, 8, 8],
[9, 9, 9, 9]]
How to do this in NumPy?
You can use numpy's repeat like this:
np.repeat(range(10), 4).reshape(10,4)
which gives:
[[0 0 0 0]
[1 1 1 1]
[2 2 2 2]
[3 3 3 3]
[4 4 4 4]
[5 5 5 5]
[6 6 6 6]
[7 7 7 7]
[8 8 8 8]
[9 9 9 9]]
You can use tile that handles dimensions:
a = np.array([0, 1, 2, 3, 4, 5])
N = 4
np.tile(a[:,None], (1, N))
# or
np.tile(a, (N, 1)).T
or broadcast_to:
np.broadcast_to(a, (N, a.shape[0])).T
# or
np.broadcast_to(a[:,None], (a.shape[0], N))
Or multiply by an array of ones:
a[:,None]*np.ones(N, dtype=a.dtype)
output:
array([[0, 0, 0, 0],
[1, 1, 1, 1],
[2, 2, 2, 2],
[3, 3, 3, 3],
[4, 4, 4, 4],
[5, 5, 5, 5]])

Get the list of all possible numpy array column deletions

Given the following numpy array:
>>> a = np.arange(9).reshape((3, 3))
>>> a
array([[0, 1, 2],
[3, 4, 5],
[6, 7, 8]])
How can get the list of all possible column deletions? So in this case:
array([[[1, 2],
[4, 5],
[7, 8]],
[[0, 2],
[3, 5],
[6, 8]],
[[0, 1],
[3, 4],
[6, 7]]])
You can use itertools.combinations:
>>> from itertools import combinations
>>> np.array([a[:, list(comb)] for comb in combinations(range(a.shape[1]), r=2)])
array([[[0, 1],
[3, 4],
[6, 7]],
[[0, 2],
[3, 5],
[6, 8]],
[[1, 2],
[4, 5],
[7, 8]]])
Alternatively you can create a list of needed column indices first and then use integer array indexing to pick up the required columns from the original array:
r = range(a.shape[1])
cols = [[j for j in r if i != j] for i in r]
cols
# [[1, 2], [0, 2], [0, 1]]
a[:, cols].swapaxes(0, 1)
#[[[1 2]
# [4 5]
# [7 8]]
#
# [[0 2]
# [3 5]
# [6 8]]
#
# [[0 1]
# [3 4]
# [6 7]]]

How can slicing dataset in TensorFlow?

I want slicing dataset in tf.data. My data is like this:
dataset = tf.data.Dataset.from_tensor_slices([[0, 1, 2, 3, 4],
[1, 2, 3, 4, 5],
[2, 3, 4, 5, 6],
[3, 4, 5, 6, 7],
[4, 5, 6, 7, 8]])
Then the main data is:
[0 1 2 3 4]
[1 2 3 4 5]
[2 3 4 5 6]
[3 4 5 6 7]
[4 5 6 7 8]
I want create other tensor dataset that contain data like this:
[[1, 2],
[2, 3],
[3, 4],
[4, 5],
[5, 6]]
In the numpy it is like this:
dataset[:,1:3]
How can do this in TensorFlow?
Update:
I do that with this:
dataset2 = dataset.map(lambda data: data[1:3])
for val in dataset2:
print(val.numpy())
But I think there is good solutions.
According to me your solution is a best solution. For the benefit of community, i am using as_numpy_iterator() method of tf.data.Dataset to slice dataset (small syntax change to your code).
Please refer code below
import tensorflow as tf
dataset = tf.data.Dataset.from_tensor_slices([[0, 1, 2, 3, 4],
[1, 2, 3, 4, 5],
[2, 3, 4, 5, 6],
[3, 4, 5, 6, 7],
[4, 5, 6, 7, 8]])
dataset2 = dataset.map(lambda data: data[1:3])
for val in dataset2.as_numpy_iterator():
print(val)
Output:
[1 2]
[2 3]
[3 4]
[4 5]
[5 6]

variable access between Function calls behavior in Python

I am doing recursion and storing the value in every step if calling.
Like if my working program-code is like-
lst=[]
def after_occurance(ls,l,curr):
for i in range(l,curr):
if ls[i]==ls[curr]:
return False
return True
def permutate(A,l,r):
if l==r:
ans=A.copy()
print(A,ans)
# change the commenting of the following 2 lines to see the difference
lst.append(A)
#lst.append(ans)
print(lst)
return lst
else:
for i in range(l,r+1):
if after_occurance(A,l,i):
A[i],A[l] = A[l],A[i]
permutate(A,l+1,r)
hm[A[l]]=1
A[l],A[i] = A[i],A[l]
else:
continue
lst.clear()
A=[1,2,6]
A=sorted(A)
permutate(A,0,len(A)-1)
return lst
Following are 2 kind of outputs when Toggling between 2 commented line respectively
[1, 2, 6] [1, 2, 6]
[[1, 2, 6]]
[1, 6, 2] [1, 6, 2]
[[1, 2, 6], [1, 6, 2]]
[2, 1, 6] [2, 1, 6]
[[1, 2, 6], [1, 6, 2], [2, 1, 6]]
[2, 6, 1] [2, 6, 1]
[[1, 2, 6], [1, 6, 2], [2, 1, 6], [2, 6, 1]]
[6, 2, 1] [6, 2, 1]
[[1, 2, 6], [1, 6, 2], [2, 1, 6], [2, 6, 1], [6, 2, 1]]
[6, 1, 2] [6, 1, 2]
[[1, 2, 6], [1, 6, 2], [2, 1, 6], [2, 6, 1], [6, 2, 1], [6, 1, 2]]
[1 2 6 ] [1 6 2 ] [2 1 6 ] [2 6 1 ] [6 1 2 ] [6 2 1 ]
[1, 2, 6] [1, 2, 6]
[[1, 2, 6]]
[1, 6, 2] [1, 6, 2]
[[1, 6, 2], [1, 6, 2]]
[2, 1, 6] [2, 1, 6]
[[2, 1, 6], [2, 1, 6], [2, 1, 6]]
[2, 6, 1] [2, 6, 1]
[[2, 6, 1], [2, 6, 1], [2, 6, 1], [2, 6, 1]]
[6, 2, 1] [6, 2, 1]
[[6, 2, 1], [6, 2, 1], [6, 2, 1], [6, 2, 1], [6, 2, 1]]
[6, 1, 2] [6, 1, 2]
[[6, 1, 2], [6, 1, 2], [6, 1, 2], [6, 1, 2], [6, 1, 2], [6, 1, 2]]
[1 2 6 ] [1 2 6 ] [1 2 6 ] [1 2 6 ] [1 2 6 ] [1 2 6 ]
Can somebody explain this behavior and what basic rule should I follow while doing Recursive calls and variable access in python?
So, this is the code you really wanted to post:
def after_occurance(ls, l, curr):
for i in range(l, curr):
if ls[i] == ls[curr]:
return False
return True
def permutate(A, l, r):
if l == r:
ans = A.copy()
# change the commenting of the following 2 lines to see the difference
#lst.append(A)
lst.append(ans)
return
else:
for i in range(l, r + 1):
if after_occurance(A, l, i):
A[i],A[l] = A[l],A[i]
permutate(A, l + 1, r)
A[l],A[i] = A[i],A[l]
else:
continue
lst = []
A = [1,2,6]
A = sorted(A)
permutate(A, 0, len(A) - 1)
print(lst)
The difference comes from appending a copy() of A or just a reference to A.
When you append a reference to A, all the future changes to A show up in lst because the result is lst = [A, A, A, A, A, ....] and so lst cannot be anything apart from a list of the same thing.
When you append a copy() of A, you make a new list which is not changed after the append() and so records the history of how A looked over time.

Python partitioning an N-dimensional volume into uniform sub-volumes

I have an object occupying an underlying N-dimensional square grid (represented by a numpy array) so that only 25% of the grid points are occupied. Each 1x1x1x... N-cube (i.e., hypercube) in this grid contains the same amount of this object (located only at some of the vertices of this hypercube). I have an array of the coordinates of all the occupied grid points. The task is to cycle through this array and extract the occupied coordinates for each 1x1x1... hypercube and store them in a new array for further processing.
The situation is best explained by example. Consider the 3-D case where the underlying grid has been chosen so that 1<=i,j,k<=4 giving the 2d numpy array:
A = [
[1 1 1]
[1 2 1]
[1 3 1]
[1 4 1]
[2 1 1]
[2 2 1]
[2 3 1]
[2 4 1]
[3 1 1]
[3 2 1]
[3 3 1]
[3 4 1]
[4 1 1]
[4 2 1]
[4 3 1]
[4 4 1]
[1 1 2]
[1 2 2]
[1 3 2]
[1 4 2]
[2 1 2]
[2 2 2]
[2 3 2]
[2 4 2]
[3 1 2]
[3 2 2]
[3 3 2]
[3 4 2]
[4 1 2]
[4 2 2]
[4 3 2]
[4 4 2]
[1 1 3]
[1 2 3]
[1 3 3]
[1 4 3]
[2 1 3]
[2 2 3]
[2 3 3]
[2 4 3]
[3 1 3]
[3 2 3]
[3 3 3]
[3 4 3]
[4 1 3]
[4 2 3]
[4 3 3]
[4 4 3]
[1 1 4]
[1 2 4]
[1 3 4]
[1 4 4]
[2 1 4]
[2 2 4]
[2 3 4]
[2 4 4]
[3 1 4]
[3 2 4]
[3 3 4]
[3 4 4]
[4 1 4]
[4 2 4]
[4 3 4]
[4 4 4]
]
An example of the 2d numpy array that I need to process in this case is:
B = [[1,1,1],[1,2,1],[1,3,1],[1,4,1],[2,2,1],[2,3,1],[2,4,1],[3,2,1],[3,3,1],[3,4,1],[4,1,1],[4,3,1],[1,1,2],[1,4,2],[2,1,2],[2,2,2],[2,4,2],[3,1,2],[3,2,2],[3,4,2],[4,1,2],[4,2,2],[4,3,2],[4,4,2],[1,1,3],[1,4,3],[2,1,3],[2,2,3],[2,3,3],[2,4,3],[3,1,3],[3,2,3],[3,3,3],[4,1,3],[4,2,3],[4,3,3],[4,4,3],[1,2,4],[1,3,4],[1,4,4],[2,1,4],[2,2,4],[2,3,4],[3,1,4],[3,2,4],[3,3,4],[4,3,4],[4,4,4]]
B is the array of the occupied grid points only. Cycling through B, I would like to get the occupied coordinates pertaining to each of the cubes of the underlying grid. The cube edges are defined by 1<=i,j,k<=2, (3<=i<=4) & (1<=j,k<=2), etc. For instance, for the cube demarcated by 1<=i,j,k<=2, I would like to extract the array [[1,1,1],[1,1,2],[1,2,1],[2,1,2],[2,2,1],[2,2,2]] from B and store it in a new array for further processing. This is then repeated until all the 8 cubes in this example are accounted for. Note that the grids are always chosen to be even so that this type of partitioning is always possible. While I can choose the grids to be even, I have no control over the site occupations by the object.
Numpy array slicing doesn't work because, in general, the grid points are not contiguous in B. I attempted a code using "for" loops to impose the ranges for the edges of the cubes but it got too complicated quickly and it doesn't seem like the right approach. Then there is the "numpy.where" function; but the complexity of the condition makes it rather intractable. Similar challenges arise with "numpy.extract".
If you have the grid as an ndim+1-dimensional array of coordinates like so
a = np.stack(np.mgrid[1:5, 1:5], -1)
then it is just a matter of judicious reshaping and transposing:
import itertools as it
# dimensions for reshape:
# split all coordinate axes into groups of two, leave the
# "dimension subscript" axis alone
chop = *it.chain.from_iterable((i//2, 2) for i in a.shape[:-1]),
# shuffle for transpose:
# regroup axes into coordinates then pairs then subscript
ax_shuf = *(1 ^ np.r_[1:4*a.ndim-3:2] % (2*a.ndim-1)), -1
# put it together and flatten, i.e. join coordinates and join pairs
a.reshape(*chop, -1).transpose(*ax_shuf).reshape(np.prod(chop[::2]), -1, a.shape[-1])
Result:
array([[[1, 1],
[1, 2],
[2, 1],
[2, 2]],
[[1, 3],
[1, 4],
[2, 3],
[2, 4]],
[[3, 1],
[3, 2],
[4, 1],
[4, 2]],
[[3, 3],
[3, 4],
[4, 3],
[4, 4]]])
Update
If B is an unordered subset of the full grid you can do the following trick:
subtract the columnwise min to make sure parity starts at even
floor divide by 2, the corners of each cube of interest will collapse into a single point
now use np.unique on the rows to get the goups
Note: If need be you can make this a bit faster by replacing argsort in the code below with one of the solutions at Most efficient way to sort an array into bins specified by an index array?.
B = np.array(B)
unq, idx, cts = np.unique((B-B.min(0))//2, axis=0, return_inverse=True, return_counts=True)
if (cts[0]==cts).all():
result = B[idx.argsort()].reshape(len(unq), cts[0], -1)
else:
result = np.split(B[idx.argsort()], cts[:-1].cumsum())
Result:
array([[[1, 1, 1],
[1, 2, 1],
[2, 2, 1],
[2, 2, 2],
[2, 1, 2],
[1, 1, 2]],
[[2, 2, 3],
[2, 1, 3],
[1, 1, 3],
[2, 1, 4],
[2, 2, 4],
[1, 2, 4]],
[[1, 4, 2],
[2, 4, 2],
[1, 3, 1],
[1, 4, 1],
[2, 3, 1],
[2, 4, 1]],
[[1, 4, 4],
[1, 3, 4],
[2, 4, 3],
[2, 3, 3],
[1, 4, 3],
[2, 3, 4]],
[[4, 1, 1],
[4, 1, 2],
[3, 2, 1],
[3, 2, 2],
[4, 2, 2],
[3, 1, 2]],
[[4, 2, 3],
[3, 2, 4],
[3, 1, 3],
[3, 2, 3],
[3, 1, 4],
[4, 1, 3]],
[[4, 4, 2],
[4, 3, 2],
[3, 4, 2],
[4, 3, 1],
[3, 4, 1],
[3, 3, 1]],
[[4, 3, 3],
[3, 3, 3],
[4, 3, 4],
[3, 3, 4],
[4, 4, 3],
[4, 4, 4]]])

Categories

Resources