web-dev-qa-db-fra.com

tf.data.Dataset: comment obtenir la taille de l'ensemble de données (nombre d'éléments dans une époque)?

Disons que j'ai défini un ensemble de données de cette façon:

filename_dataset = tf.data.Dataset.list_files("{}/*.png".format(dataset))

comment puis-je obtenir le nombre d'éléments qui se trouvent à l'intérieur de l'ensemble de données (d'où le nombre d'éléments uniques qui composent une époque)?

Je sais que tf.data.Dataset Connaît déjà la dimension de l'ensemble de données, car la méthode repeat() permet de répéter le pipeline d'entrée pour un nombre spécifié d'époques. Ce doit donc être un moyen d'obtenir ces informations.

9
nessuno

tf.data.Dataset.list_files Crée un tenseur appelé MatchingFiles:0 (Avec le préfixe approprié le cas échéant).

Vous pourriez évaluer

tf.shape(tf.get_default_graph().get_tensor_by_name('MatchingFiles:0'))[0]

pour obtenir le nombre de fichiers.

Bien sûr, cela ne fonctionnerait que dans des cas simples, et en particulier si vous n'avez qu'un seul échantillon (ou un nombre connu d'échantillons) par image.

Dans des situations plus complexes, par ex. lorsque vous ne connaissez pas le nombre d'échantillons dans chaque fichier, vous ne pouvez observer le nombre d'échantillons qu'à la fin d'une époque.

Pour ce faire, vous pouvez regarder le nombre d'époques compté par votre Dataset. repeat() crée un membre appelé _count, qui compte le nombre d'époques. En l'observant pendant vos itérations, vous pouvez repérer quand il change et calculer la taille de votre jeu de données à partir de là.

Ce compteur peut être enterré dans la hiérarchie de Datasets qui est créée lors de l'appel successif des fonctions membres, nous devons donc le creuser comme ceci.

d = my_dataset
# RepeatDataset seems not to be exposed -- this is a possible workaround 
RepeatDataset = type(tf.data.Dataset().repeat())
try:
  while not isinstance(d, RepeatDataset):
    d = d._input_dataset
except AttributeError:
  warnings.warn('no Epoch counter found')
  Epoch_counter = None
else:
  Epoch_counter = d._count

Notez qu'avec cette technique, le calcul de la taille de votre jeu de données n'est pas exact, car le lot pendant lequel Epoch_counter Est incrémenté mélange généralement des échantillons de deux époques successives. Ce calcul est donc précis jusqu'à la longueur de votre lot.

4
P-Gn

len(list(dataset)) fonctionne en mode impatient, bien que ce ne soit évidemment pas une bonne solution générale.

4
markemus

Malheureusement, je ne pense pas qu'il existe encore une telle fonctionnalité dans TF. Cependant, avec TF 2.0 et une exécution rapide, vous pouvez simplement parcourir le jeu de données:

num_elements = 0
for element in dataset:
    num_elements += 1

C'est le moyen le plus efficace de stockage que j'ai pu trouver

Cela ressemble vraiment à une fonctionnalité qui aurait dû être ajoutée il y a longtemps. Les doigts croisés, ils ajoutent cette fonction de longueur dans une version ultérieure.

2
RodYt

Jetez un œil ici: https://github.com/tensorflow/tensorflow/issues/26966

Cela ne fonctionne pas pour les jeux de données TFRecord, mais cela fonctionne bien pour d'autres types.

TL; DR:

num_elements = tf.data.experimental.cardinality (jeu de données) .numpy ()

0