N = np.random.choice([0,1,2,3,4], 5000, p=[i/sum(range(1,6)) for i in range(1,6)])
plt.hist(N, density=True, bins=5)
plt.grid()
T = tf.random.categorical(tf.math.log([[i/sum(range(1,6)) for i in range(1,6)]]), 5000)
# T = tf.random.categorical([[i/sum(range(1,6)) for i in range(1,6)]], 1000)
plt.hist(T, density=True, bins=5)
plt.grid()
def random_choice(a, size):
"""Random choice from 'a' based on size without duplicates
Args:
a: Tensor
size: int or shape as tuple of ints e.g., (m, n, k).
Returns: Tensor of the shape specified with 'size' arg.
Examples:
X = tf.constant([[1,2,3],[4,5,6]])
random_choice(X, (2,1,2)).numpy()
-----
[
[
[5 4]
],
[
[1 2]
]
]
"""
if isinstance(size, int) or np.issubdtype(type(a), np.integer) or (tf.is_tensor(a) and a.shape == () and a.dtype.is_integer):
shape = (size,)
elif isinstance(size, tuple) and len(size) > 0:
shape = size
else:
raise AssertionError(f"Unexpected size arg {size}")
sample_size = tf.math.reduce_prod(size, axis=None)
assert sample_size > 0
# --------------------------------------------------------------------------------
# Select elements from a flat array
# --------------------------------------------------------------------------------
a = tf.reshape(a, (-1))
length = tf.size(a)
assert sample_size <= length
# --------------------------------------------------------------------------------
# Shuffle a sequential numbers (0, ..., length-1) and take size.
# To select 'sample_size' elements from a 1D array of shape (length,),
# TF Indices needs to have the shape (sample_size,1) where each index
# has shape (1,),
# --------------------------------------------------------------------------------
indices = tf.reshape(
tensor=tf.random.shuffle(tf.range(0, length, dtype=tf.int32))[:sample_size],
shape=(-1, 1) # Convert to the shape:(sample_size,1)
)
return tf.reshape(tensor=tf.gather_nd(a, indices), shape=shape)
X = tf.constant([[1,2,3],[4,5,6]])
print(random_choice(X, (2,2,1)).numpy())
---
[[[5]
[4]]
[[2]
[1]]]