C++ Comment allouer de la mémoire dynamiquement sur la pile?
Est-il un moyen pour allouer de la mémoire sur pile au lieu de tas? Je ne peux pas trouver un bon livre sur ce, quelqu'un ici a une idée?
- Si vous voulez contrôler où un std::string ou std::vector alloue de la mémoire, cochez cette question: stackoverflow.com/questions/354442/...
- rapidement allouer/libre temporaire de l'espace de travail?
- Butterworth Exemple: vous devez allouer un certain montant variable de l'espace pour un tampon temporaire pendant que vous trier les sommets en fonction de la profondeur. Les sommets venir de l'exécution des données, de sorte que vous ne connaissez pas à l'avance combien vous aurez. Aussi, vous disposez d'un budget de 2 microsecondes pour l'ensemble de la fonction, et sur votre plate-forme de malloc() coûts de 1 microseconde.
- Donc, il suffit de créer des objets locaux comme d'habitude - pas besoin d'installations spéciales.
- Je ne pense pas que vous pouvez mettre en œuvre un allocateur qui utilise
alloca
. La mémoire allouée ne peut être utilisé à l'intérieur de la fonction qui alloue, de sorte que le tampon ne peut pas être retourné à partir de l'allocateur! - et si la fonction a besoin d'un petit, mais variable, le nombre d'objets temporaires? Vous pouvez utiliser un
vector
, mais si la fonction est appelée dans une boucle serrée, ce serait cool si la mémoire peut être rapidement allouée et libéré sans se soucier de la fragmentation. - La accepté de répondre à cette question n'implique pas alloca.
- ce que l'OP a demandé implique nécessairement
alloca
. - Alors allouer un petit, mais le fixe, le nombre d'objets sur la pile. Si nous ne savons pas la limite supérieure, alloca va souffler de toute façon.
- Il y a beaucoup de questions sur StackOverflow où la question posée n'est pas ce que l'interlocuteur réellement nécessaire.
- bien sûr, mais qui introduit un supplément de nombre magique dans le code, et à la limite varie en fonction de la machine, les drapeaux de compilation, etc. (tout ce qui peut influencer la taille de la pile). Si je cultive les taille de la pile, j'aurais maintenant besoin de changer les 2 ensembles de paramètres: la taille de la pile et la limite codée en dur pour ma fonction.
std::queue
et la récursivité peut-être en tant que cet objet est conçu pour être rapide continue d'allocation. Remarque en C++new
etdelete
sont utilisés pour l'allocation de tas peut-être cela devrait être ré-étiquetés comme C.alloca
est largement utilisé dans Microsoft Windows, pour chaîne temporaire de zones tampons pour la traduction entre UTF-16 et Windows ANSI.- J'ai été à la programmation Windows depuis la version 2.0 et ne l'ai jamais utilisé, ou vu utilisé.,
- Je suppose que tous ces appels sont cachés dans les versions ANSI de la Win32API, puisque le noyau traite uniquement les versions Unicode.
- André dit. En outre, pour votre propre usage, je me souviens de MFC et ATL définir un groupe de macros que le paquet de la
alloca
appels. Je peux regarder si tu veux, mais depuis que je sais que vous êtes assez bon, je ne perds pas de temps à ça pour le moment. Cheers,
Vous devez vous connecter pour publier un commentaire.
Utilisation
alloca()
(parfois appelé_alloca()
ou_malloca()
), mais être très prudent à ce sujet — il libère sa mémoire lorsque vous quittez une fonction, pas quand vous sortez de la portée, de sorte que vous allez vite exploser si vous l'utilisez à l'intérieur d'une boucle.Par exemple, si vous avez une fonction comme
Puis l'alloca() va allouer un supplémentaires nDataSize octets chaque passage dans la boucle. Aucun des alloca() octets être libéré jusqu'à ce que vous êtes de retour de la fonction. Donc, si vous avez un
nDataSize
de 1024 et uniterations
de 8, vous allez allouer de 8 kilo-octets avant de retourner. Si vous avez unnDataSize
= 65536 etiterations
= 32768, vous allez allouer un total de 65536×32768=2,147,483,648 octets, presque certainement le soufflage de votre pile et de provoquer un incident.anecdote: Vous pouvez facilement avoir des ennuis si vous écrivez passé la fin de la mémoire tampon, surtout si vous passez le tampon dans une autre fonction, et que la sous-fonction a la mauvaise idée au sujet de la mémoire tampon de longueur. Une fois, j'ai fixé un plutôt amusant bug où nous avons été à l'aide de
alloca()
pour créer de stockage temporaire pour le rendu d'une police TrueType glyphe avant de l'envoyer à la mémoire GPU. Notre bibliothèque de polices n'ai pas de compte pour les diacritiques dans le suédois Å personnage lors du calcul de la glyphe de tailles, de sorte qu'il nous a dit de nous allouer n octets pour stocker la glyphe avant le rendu, et puis effectivement rendu n+128 octets. Le supplément de 128 octets écrit dans la pile d'appel, écraser l'adresse de retour et d'induire un vraiment douloureux non déterministe crash!std::vector
locale à la boucle sera libéré à la fin de la boucle de la portée).Puisque c'est marqué, C++, généralement, il suffit de déclarer les objets dont vous avez besoin dans le domaine approprié. Ils sont allouées sur la pile, et la garantie d'être libéré sur le champ de sortie. C'est RAII, et une critique avantage du C++ sur C. Pas de
malloc
s ounew
s, et surtout pas dealloca
s, nécessaire.Vous pouvez déclarer un local
char[1024]
ou quel que soit le nombre d'octets que vous souhaitez (jusqu'à un certain point), puis prendre l'adresse du local pour un pointeur vers ce bloc de mémoire sur la pile. Pas exactement dynamique, mais vous pouvez envelopper ce mémoire avec votre propre gestionnaire de mémoire si vous le souhaitez.Article discutant sur l'allocation dynamique de la mémoire
Si le C++ permet l'utilisation de (non statique)
const
valeurs limites du tableau, il sera plus facile.Pour l'instant, le meilleur moyen que je connaisse est via la récursivité. Il y a toutes sortes de trucs astucieux qui peut être fait, mais le plus simple que je connaisse est à votre routine de déclarer une taille fixe de tableau, et de le remplir et de fonctionner sur ce qu'il a fait. Quand c'est fait, si il a besoin de plus d'espace à la fin, il appelle lui-même.
size_t const
et ensuite l'utiliser comme un tableau de la taille de l'index?static const
où vous signifiait localconst
comme dansvoid f(const int n) { ... }
.const int N = 42; char a[N];
int a[n];
oùn
est variable au moment de l'exécution. Et comme j'aime standardese et de pédantisme autant que la prochaine personne, je suppose que tu savais ce que je voulais dire 🙂Vous pouvez utiliser le BDE de la bibliothèque C++, par exemple
BDE fournit des allocateur options, ainsi que des collections comme bsl::vector qui peut utiliser polymorphes allocateurs sans changer le type de conteneur.
Vous pourriez aussi envisager d':
Voir
_malloca
.