Contexte: J'écris du code C de micro contrôleur pour écrire un fichier EBML. EBML est comme un XML binaire avec des éléments imbriqués, mais au lieu des balises de début et de fin, il y a un ID de début, une longueur, puis les données. J'écris ceci dans un flash externe dans une application à faible puissance, donc je voudrais garder les accès au flash au minimum. La mémoire est également limitée, car rien n'est jamais facile.
Quand je peux garder la totalité de l'élément EBML en mémoire, il est facile de le générer car je peux revenir en arrière et remplir la longueur de chaque élément une fois que je sais quelle est cette longueur. Le problème est de savoir quoi faire quand je ne peux pas garder l'élément entier en mémoire. Les options que je vois sont:
- Écrivez ce que je sais, puis revenez en arrière et ajoutez les longueurs (le plus simple, mais ajoute plus d'accès flash que je ne le souhaite)
- Calculez la longueur de chaque élément avant de commencer à l'écrire (relativement facile, mais beaucoup de temps processeur)
- Changez de mode une fois que ma mémoire se remplit, pour que je continue ensuite à parcourir les données, mais uniquement pour calculer les longueurs des éléments déjà réservés en mémoire. Ensuite, écrivez ce que j'ai en mémoire et revenez en arrière et continuez à traiter les données là où je les avais laissées. (Mon option préférée jusqu'à présent)
- Donnez aux éléments une longueur maximale ou la pire des cas lorsqu'ils doivent être écrits et que leur longueur finale n'est pas encore connue. (Plus facile que ci-dessus, mais pourrait se retourner contre vous et gaspiller de l'espace)
Question: Il semble que cela devrait être un problème relativement courant auquel les gens ont pensé. Je sais que cela peut également se produire lors de la formation de certains paquets de données. Y a-t-il une technique meilleure / plus courante / plus acceptée qui me manque ici? Ou juste quelques termes pour le problème que je peux rechercher?
la source
Réponses:
Si vous ne savez pas combien de temps durera votre charge utile, cela vous inquiète rarement même si vous ne vous souvenez plus de la position et ne remblayez pas la longueur plus tard:
Notez simplement "taille inconnue".
Cette fonctionnalité dépend de la charge utile constituée des éléments EBML et l'élément suivant n'est cependant pas un élément enfant valide.
Si vous le souhaitez, vous pouvez ultérieurement canoniser l'EBML résultant hors ligne à votre convenance comme vous le souhaitez, par exemple pour "pas de tailles inconnues, taille minimale" ou "taille minimale, éviter les tailles inconnues".
Reportez-vous au projet EBML RFC sur matroska.org pour plus de détails.
la source
Si un seul élément avec un nombre fixe de sous-éléments est trop grand, alors vous devriez peut-être essayer de le diviser en schéma. Je ne connais pas ce format, mais vous pouvez très probablement y définir une longueur maximale.
Pour les séquences, vous pouvez essayer de définir le nombre maximal de sous-éléments et le "flux" restant dans le fichier suivant
Pour les éléments dépassant potentiellement la taille maximale de la mémoire, préparez une pile contenant des paires: emplacement de longueur d'élément réservé et compteur de longueur. À la pop, enregistrez le compteur actuel dans le marqueur actuel et ajoutez sa valeur au compteur suivant.
En général, essayez de minimiser le nombre d'éléments trop gros
la source
KISS et YAGNI.
Choisissez l'option # 1 et si cela devient un vrai problème - réitérez-la ensuite.
Au moins pour des cas d'utilisation similaires avec des formats binaires similaires, lorsque seulement quelques valeurs devaient être remplies de cette manière, c'est la solution la plus simple / la plus facile / la meilleure. Si vous devez le faire sur chaque morceau de données - cela pourrait être une faille dans l'architecture.
la source