Comment obtenir la taille d'un objet JavaScript?

298

Je veux connaître la taille occupée par un objet JavaScript.

Prenez la fonction suivante:

function Marks(){
  this.maxMarks = 100;
}

function Student(){
  this.firstName = "firstName";
  this.lastName = "lastName";
  this.marks = new Marks();
}

Maintenant, j'instancie le student:

var stud = new Student();

pour que je puisse faire des trucs comme

stud.firstName = "new Firstname";

alert(stud.firstName);

stud.marks.maxMarks = 200;

etc.

Maintenant, l' studobjet occupera une certaine taille en mémoire. Il contient des données et d'autres objets.

Comment savoir combien de mémoire l’ studobjet occupe? Quelque chose comme un sizeof()en JavaScript? Ce serait vraiment génial si je pouvais le découvrir en un seul appel de fonction comme sizeof(stud).

Je recherche sur Internet depuis des mois - je ne l'ai pas trouvé (demandé dans quelques forums - pas de réponse).

user4642212
la source
41
Il y a (se posera) de nombreuses raisons pour lesquelles je dois trouver la taille d'un objet en JavaScript. Je suis nouveau sur JavaScript, donc je ne respecte pas les meilleures pratiques. Je les apprends encore. J'ai développé une extension firefox qui, j'en suis sûr, utilise plus de mémoire qu'elle ne le devrait. Je travaille sur quelques façons de (espérons-le) réduire l'utilisation de la mémoire. Je parle de milliers d'instances, de nombreux objets par onglet, donc la mémoire est importante! Le truc, c'est que je veux savoir si mes efforts de réduction de mémoire aident réellement à réduire la mémoire .. et de combien.
1
Si vous avez construit une extension FF, je vous conseille d'enquêter à un niveau de langue plus élevé que JS - voyez quel est l'impact sur FF lui-même.
annakata
2
Langage de niveau supérieur à JS? qu'est-ce que ce serait dans ce cas?
24
Ce n'est pas la taille qui compte de toute façon. C'est ainsi que vous l'utilisez. PS: Quel étalon!
Thomas Eding
13
@SpencerRuport La première raison de connaître la taille de l'objet serait pour les applications compatibles html5 hors ligne où vous avez parfois un espace de stockage limité (5 à 10 Mo peuvent être consommés rapidement pour une application gourmande en données).
David

Réponses:

182

J'ai refactorisé le code dans ma réponse d'origine . J'ai supprimé la récursivité et supprimé la surcharge d'existence supposée.

function roughSizeOfObject( object ) {

    var objectList = [];
    var stack = [ object ];
    var bytes = 0;

    while ( stack.length ) {
        var value = stack.pop();

        if ( typeof value === 'boolean' ) {
            bytes += 4;
        }
        else if ( typeof value === 'string' ) {
            bytes += value.length * 2;
        }
        else if ( typeof value === 'number' ) {
            bytes += 8;
        }
        else if
        (
            typeof value === 'object'
            && objectList.indexOf( value ) === -1
        )
        {
            objectList.push( value );

            for( var i in value ) {
                stack.push( value[ i ] );
            }
        }
    }
    return bytes;
}
thomas-peter
la source
35
vous voudrez peut-être aussi penser aux clés des objets
zupa
8
Quiconque a atterri ici à la recherche du plus petit type aux fins de faux / vrai, il semble être indéfini / nul.
zupa
3
"よんもじ".lengthest 4 en Javascript, mais êtes-vous sûr que c'est 8 octets, comme votre code le renvoie?
syockit
8
Oui. Les caractères en JavaScript sont stockés conformément à la spécification ECMA-262 3rd Edition - bclary.com/2004/11/07/#a-4.3.16
thomas-peter
4
Cette fonction ne compte pas les références cachées dans les fermetures. Par exemple var a={n:1}; var b={a:function(){return a}}; roughSizeOfObject(b)- bcontient ici une référence à a, mais roughSizeOfObject()retourne 0.
Roman Pominov
118

Google Chrome Heap Profiler vous permet d'inspecter l'utilisation de la mémoire des objets.

Vous devez pouvoir localiser l'objet dans la trace, ce qui peut être délicat. Si vous épinglez l'objet à la fenêtre globale, il est assez facile à trouver à partir du mode de liste "Contention".

Dans la capture d'écran ci-jointe, j'ai créé un objet appelé "testObj" sur la fenêtre. Je l'ai ensuite localisé dans le profileur (après avoir fait un enregistrement) et il montre la pleine taille de l'objet et tout ce qu'il contient sous "taille retenue".

Plus de détails sur les pannes de mémoire .

Profileur Chrome

Dans la capture d'écran ci-dessus, l'objet affiche une taille conservée de 60. Je pense que l'unité est ici en octets.

Guy Bedford
la source
13
Cette réponse a résolu mon problème avec: developers.google.com/chrome-developer-tools/docs/… . Astuce rapide: prenez un instantané de tas rapide, exécutez la tâche que vous soupçonnez de fuir, prenez un nouvel instantané de tas rapide et sélectionnez la comparisonvue en bas. Il rend évident quels objets ont été créés entre les deux instantanés.
Johnride
1
C'est probablement la solution la plus propre.
Luca Steeb du
La comparaison, mentionnée par @Johnride, est maintenant un menu déroulant en haut.
frandroid
Shallow sizesemble que 40 pour les deux { a:"55c2067aee27593c03b7acbe", b:"55c2067aee27593c03b7acbe", c:null, d:undefined }et les { c:null, d:undefined }objets. Est-ce que c'est bon?
efkan
1
Vous pouvez également utiliser le profileur de tas Google Chrome à partir du nœud. Si vous avez un nœud v8 ou supérieur, démarrez-le avec node --inspectet dans Chrome, entrez about:inspectdans la barre d'URL et recherchez l'ouverture de l'inspecteur de nœud. Créez votre objet dans la CLI du nœud, puis prenez un instantané de segment de mémoire.
Gregor
75

Je viens d'écrire ceci pour résoudre un problème similaire (ish). Il ne fait pas exactement ce que vous cherchez, c'est-à-dire qu'il ne prend pas en compte la façon dont l'interpréteur stocke l'objet.

Mais, si vous utilisez V8, cela devrait vous donner une approximation assez correcte, car le génial prototypage et les classes cachées lèchent la majeure partie de la surcharge.

function roughSizeOfObject( object ) {

    var objectList = [];

    var recurse = function( value )
    {
        var bytes = 0;

        if ( typeof value === 'boolean' ) {
            bytes = 4;
        }
        else if ( typeof value === 'string' ) {
            bytes = value.length * 2;
        }
        else if ( typeof value === 'number' ) {
            bytes = 8;
        }
        else if
        (
            typeof value === 'object'
            && objectList.indexOf( value ) === -1
        )
        {
            objectList[ objectList.length ] = value;

            for( i in value ) {
                bytes+= 8; // an assumed existence overhead
                bytes+= recurse( value[i] )
            }
        }

        return bytes;
    }

    return recurse( object );
}
thomas-peter
la source
1
@Liangliang Zheng - grand point re boucle infinie, merci. J'espère que cela ne vous dérange pas si je le rejoue un peu et met à jour le mien après le travail (?)
thomas-peter
Je vais tester ce soir avec node.js et obtenir de meilleurs coefficients en place.
thomas-peter
La ligne 'octets + = recurse (valeur [i])', génère une erreur dans mon FF 14.01: NS_ERROR_FAILURE: le composant a renvoyé le code d'échec: 0x80004005 (NS_ERROR_FAILURE) [nsIDOMHTMLInputElement.selectionStart]. Sur l'un de mes objets, si j'en essaie un autre, ce n'est pas le cas, peut-être un bug de navigateur, ou le code ne fonctionne pas pour chaque objet (celui qui ne fonctionne pas contient des fonctions, celui qui fonctionne ne fonctionne pas). t)
TrySpace
1
D'un Tom à l'autre, cela s'est révélé très utile comme indicateur approximatif de l'endroit où je devais couper la taille de mon objet. Votre miss a-t-elle donc découvert votre liaison avec Javascript? C'est une maîtresse qui demande beaucoup d'entretien.
Tom W Hall
4
C'est PHP (gulp) que je dois surveiller - j'ai cessé de l'aimer il y a longtemps mais elle paie les factures. Quoi qu'il en soit, merci Tom, des commentaires qui sont bien meilleurs que des points de réputation.
thomas-peter
55

Parfois, j'utilise ceci pour signaler de très gros objets qui pourraient être envoyés au client depuis le serveur. Il ne représente pas l'empreinte mémoire. Il vous donne juste environ ce qu'il en coûterait pour l'envoyer ou le stocker.

Notez également que c'est lent, uniquement pour les développeurs. Mais pour obtenir une réponse approximative avec une seule ligne de code, cela m'a été utile.

roughObjSize = JSON.stringify(bigObject).length;
zstew
la source
2
D'après mes tests, cette méthode est considérablement plus rapide que le cas de la taille de l'objet car elle n'a pas l'appel lent _.isObject () de lodash. De plus, les tailles retournées sont assez comparables pour des estimations approximatives. Gist gist.github.com/owenallenaz/ff77fc98081708146495 .
Nucleon
5
Ne peut pas être utilisé avec des structures circulaires VM1409:1 Uncaught TypeError: Converting circular structure to JSON:( toujours utile cependant
givanse
ce n'est pas une taille binaire en octets mais simple à utiliser pour obtenir une taille approximative
datdinhquoc
C'est très bien si 1) vous avez seulement besoin d'une estimation approximative 2) vous savez que vous n'avez pas de références circulaires 3) vous pouvez omettre de grandes valeurs et les messurer séparément. Tout cela était vrai dans mon cas, cela fonctionne donc parfaitement, je n'avais qu'une seule grosse chaîne à un endroit sur laquelle je peux simplement mesurer la longueur.
OZZIE
45

Voici une solution légèrement plus compacte au problème:

const typeSizes = {
  "undefined": () => 0,
  "boolean": () => 4,
  "number": () => 8,
  "string": item => 2 * item.length,
  "object": item => !item ? 0 : Object
    .keys(item)
    .reduce((total, key) => sizeOf(key) + sizeOf(item[key]) + total, 0)
};

const sizeOf = value => typeSizes[typeof value](value);
Dan
la source
3
c'est donc la taille en Ko? ou des morceaux?
vincent thorpe du
2
@ vincent-thorpe C'est en octets.
Dan
3
Beau script, nécessite cependant des modifications pour les références cycliques.
Jim Pedid
1
Je viens de tester votre algorithme sur une vaste gamme de données dans un processus de nœud, il rapporte 13 Go, mais le nœud consomme 22 Go, une idée d'où vient la différence? Il n'y a plus rien en mémoire.
Josu Goñi
3
@ JosuGoñi, ils ne calculent pas combien l'objet lui-même prend, seulement sa valeur. Tous les objets prennent plus d'espace que leur valeur, sinon typeof ...cela ne fonctionnerait pas.
Alexis Wilke
43

Il existe un module NPM pour obtenir la taille de l'objet , vous pouvez l'installer avecnpm install object-sizeof

  var sizeof = require('object-sizeof');

  // 2B per character, 6 chars total => 12B
  console.log(sizeof({abc: 'def'}));

  // 8B for Number => 8B
  console.log(sizeof(12345));

  var param = { 
    'a': 1, 
    'b': 2, 
    'c': {
      'd': 4
    }
  };
  // 4 one two-bytes char strings and 3 eighth-bytes numbers => 32B
  console.log(sizeof(param));
Andrei Karpushonak
la source
sizeof (new Date ()) === 0 et sizeof ({}) === 0. Est-ce prévu?
Philipp Claßen
1
@ PhilippClaßen C'est évidemment le cas. Les deux objets n'ont aucune propriété.
Robert
18

C'est une méthode hacky, mais je l'ai essayée deux fois avec des nombres différents et elle semble cohérente.

Ce que vous pouvez faire est d'essayer d'allouer un grand nombre d'objets, comme un ou deux millions d'objets du type que vous souhaitez. Mettez les objets dans un tableau pour empêcher le garbage collector de les libérer (notez que cela ajoutera une légère surcharge de mémoire à cause du tableau, mais j'espère que cela ne devrait pas avoir d'importance et d'ailleurs si vous allez vous inquiéter que des objets soient en mémoire , vous les stockez quelque part). Ajoutez une alerte avant et après l'allocation et vérifiez à chaque alerte la quantité de mémoire nécessaire au processus Firefox. Avant d'ouvrir la page avec le test, assurez-vous d'avoir une nouvelle instance de Firefox. Ouvrez la page, notez l'utilisation de la mémoire après l'affichage de l'alerte "avant". Fermez l'alerte, attendez que la mémoire soit allouée. Soustrayez la nouvelle mémoire de l'ancienne et divisez-la par le nombre d'allocations.

function Marks()
{
  this.maxMarks = 100;
}

function Student()
{
  this.firstName = "firstName";
  this.lastName = "lastName";
  this.marks = new Marks();
}

var manyObjects = new Array();
alert('before');
for (var i=0; i<2000000; i++)
    manyObjects[i] = new Student();
alert('after');

J'ai essayé cela sur mon ordinateur et le processus avait 48352 Ko de mémoire lorsque l'alerte "avant" a été affichée. Après l'allocation, Firefox avait 440236 Ko de mémoire. Pour 2 millions d'allocations, cela représente environ 200 octets pour chaque objet.

Je l'ai essayé à nouveau avec 1 million d'allocations et le résultat était similaire: 196 octets par objet (je suppose que les données supplémentaires dans 2mill ont été utilisées pour Array).

Alors, voici une méthode hacky qui pourrait vous aider. JavaScript ne fournit pas de méthode "sizeof" pour une raison: chaque implémentation JavaScript est différente. Dans Google Chrome par exemple, la même page utilise environ 66 octets pour chaque objet (à en juger par le gestionnaire de tâches au moins).

Mauvais secteur
la source
Hé .. merci pour la technique. J'avais cela comme plan B dans le cas où aucun moyen direct n'était là pour mesurer l'utilisation de la mémoire.
4
Chaque implémentation C et C ++ est également différente. ;) La taille d'un type de données en C ou C ++ est spécifique à l'implémentation. Je ne vois aucune raison pour laquelle JavaScript ne pourrait pas prendre en charge un tel opérateur, même s'il ne servirait pas le même objectif ou n'aurait pas la même signification qu'en C ou C ++ (qui sont des langages de niveau inférieur et mesurent la taille réelle d'un fixe). taille du type de données au moment de la compilation par opposition à la taille variable d'un objet JavaScript dynamique au moment de l'exécution).
bambams
12

Désolé, je n'ai pas pu commenter, je continue donc le travail de tomwrong. Cette version améliorée ne comptera pas les objets plus d'une fois, donc pas de boucle infinie. De plus, je pense que la clé d'un objet doit également être comptée, en gros.

function roughSizeOfObject( value, level ) {
    if(level == undefined) level = 0;
    var bytes = 0;

    if ( typeof value === 'boolean' ) {
        bytes = 4;
    }
    else if ( typeof value === 'string' ) {
        bytes = value.length * 2;
    }
    else if ( typeof value === 'number' ) {
        bytes = 8;
    }
    else if ( typeof value === 'object' ) {
        if(value['__visited__']) return 0;
        value['__visited__'] = 1;
        for( i in value ) {
            bytes += i.length * 2;
            bytes+= 8; // an assumed existence overhead
            bytes+= roughSizeOfObject( value[i], 1 )
        }
    }

    if(level == 0){
        clear__visited__(value);
    }
    return bytes;
}

function clear__visited__(value){
    if(typeof value == 'object'){
        delete value['__visited__'];
        for(var i in value){
            clear__visited__(value[i]);
        }
    }
}

roughSizeOfObject(a);
Liangliang Zheng
la source
Je pense que c'est plus précis car il compte les clés, bien qu'il compte la clé '__visited__'
Sam Hasler
La vérification typeof value === 'object'ne suffit pas et vous aurez des exceptions si la valeur est null.
floribon
C'était extrêmement rapide pour mon objet (dont je suis assez sûr d'avoir plus de 5 Mo), en comparaison avec l'une des réponses dupées de @ tomwrong. Il était également plus précis (comme il disait environ 3 Mo) mais encore trop loin de la réalité. Des indices sur ce que cela ne compte peut-être pas?
cregox
Ça ne marche pas pour moi. L'objet levelcontient des données mais roughSizeOfObject(level)renvoie zéro. (Mon niveau de variable ne doit pas être confondu avec votre argument, bien sûr. Je ne pense pas que l'observation des variables devrait causer un problème ici, et aussi lorsque je renomme le 'niveau' dans votre script, j'obtiens le même résultat.) Capture d'écran : snipboard.io/G7E5yj.jpg
Luc
11

Ayant le même problème. J'ai cherché sur Google et je souhaite partager avec la communauté stackoverflow cette solution.

Important :

J'ai utilisé la fonction partagée par Yan Qing sur github https://gist.github.com/zensh/4975495

function memorySizeOf(obj) {
    var bytes = 0;

    function sizeOf(obj) {
        if(obj !== null && obj !== undefined) {
            switch(typeof obj) {
            case 'number':
                bytes += 8;
                break;
            case 'string':
                bytes += obj.length * 2;
                break;
            case 'boolean':
                bytes += 4;
                break;
            case 'object':
                var objClass = Object.prototype.toString.call(obj).slice(8, -1);
                if(objClass === 'Object' || objClass === 'Array') {
                    for(var key in obj) {
                        if(!obj.hasOwnProperty(key)) continue;
                        sizeOf(obj[key]);
                    }
                } else bytes += obj.toString().length * 2;
                break;
            }
        }
        return bytes;
    };

    function formatByteSize(bytes) {
        if(bytes < 1024) return bytes + " bytes";
        else if(bytes < 1048576) return(bytes / 1024).toFixed(3) + " KiB";
        else if(bytes < 1073741824) return(bytes / 1048576).toFixed(3) + " MiB";
        else return(bytes / 1073741824).toFixed(3) + " GiB";
    };

    return formatByteSize(sizeOf(obj));
};


var sizeOfStudentObject = memorySizeOf({Student: {firstName: 'firstName', lastName: 'lastName', marks: 10}});
console.log(sizeOfStudentObject);

Qu'est-ce que tu en penses?

Ala Eddine JEBALI
la source
3
Cela manque des fonctions. Si j'ajoute une fonction, l'objet n'apparaît pas comme plus grand
Don Rhummy
Ne compte pas les clés
ebg11
7

je veux savoir si mes efforts de réduction de la mémoire aident réellement à réduire la mémoire

Suite à ce commentaire, voici ce que vous devez faire: Essayez de produire un problème de mémoire - Écrivez du code qui crée tous ces objets et augmentez grossièrement la limite supérieure jusqu'à ce que vous rencontriez un problème (crash du navigateur, gel du navigateur ou un out-of- erreur de mémoire). Idéalement, vous devriez répéter cette expérience avec différents navigateurs et différents systèmes d'exploitation.

Maintenant, il y a deux options: option 1 - Vous n'avez pas réussi à produire le problème de mémoire. Par conséquent, vous vous inquiétez pour rien. Vous n'avez pas de problème de mémoire et votre programme va bien.

option 2 - vous avez eu un problème de mémoire. Demandez-vous maintenant si la limite à laquelle le problème s'est produit est raisonnable (en d'autres termes: est-il probable que cette quantité d'objets soit créée lors d'une utilisation normale de votre code). Si la réponse est «non», alors ça va. Sinon, vous savez maintenant combien d'objets votre code peut créer. Retravaillez l'algorithme de sorte qu'il ne dépasse pas cette limite.

Itay Maman
la source
Du point de vue de la mémoire, mon extension ajoute un certain nombre d'objets pour chaque page / onglet ouvert dans Firefox. Le "nombre" est proportionnel à la taille de la page. En supposant que les utilisateurs "puissants" aient entre 15 et 20 onglets ouverts, et si la page Web contient beaucoup de contenu, le navigateur devient lent et frustrant de ne plus répondre après un certain temps. Cela se produit même sans que j'essaie explicitement de souligner l'application. J'ai l'intention de réécrire le code qui, je pense, réduira beaucoup la création d'objets. Je voulais juste être sûr que non. des objets réduits équivalaient à quelque chose pour que cela en vaille la peine
@Senthil: mais la taille de l'objet n'a de sens que si vous connaissez la quantité de mémoire disponible. Étant donné que la quantité de mémoire restera probablement un mystère, parler en termes de #objects est tout aussi utile que de parler en termes de #bytes
Itay Maman
5

Cette bibliothèque Javascript sizeof.jsfait la même chose. Incluez-le comme ceci

<script type="text/javascript" src="sizeof.js"></script>

La fonction sizeof prend un objet comme paramètre et renvoie sa taille approximative en octets. Par exemple:

// define an object
var object =
    {
      'boolean' : true,
      'number'  : 1,
      'string'  : 'a',
      'array'   : [1, 2, 3]
    };

// determine the size of the object
var size = sizeof(object);

La fonction sizeof peut gérer des objets qui contiennent plusieurs références à d'autres objets et des références récursives.

Publié à l'origine ici .

Jayram
la source
Ceci est plus lent et semble être «moins précis» que celui de @liangliang, dans mon cas d'utilisation.
cregox
2

Un grand merci à tous ceux qui ont travaillé sur le code pour cela!

Je voulais juste ajouter que je cherchais exactement la même chose, mais dans mon cas, c'est pour gérer un cache d'objets traités pour éviter d'avoir à ré-analyser et traiter des objets d'appels ajax qui peuvent ou non avoir été mis en cache par le navigateur. Ceci est particulièrement utile pour les objets qui nécessitent beaucoup de traitement, généralement tout ce qui n'est pas au format JSON, mais il peut être très coûteux de garder ces choses en cache dans un grand projet ou une application / extension qui reste en cours d'exécution pendant une longue période. temps.

Quoi qu'il en soit, je l'utilise pour quelque chose comme:

var myCache = {
    cache: {},
    order: [],
    size: 0,
    maxSize: 2 * 1024 * 1024, // 2mb

    add: function(key, object) {
        // Otherwise add new object
        var size = this.getObjectSize(object);
        if (size > this.maxSize) return; // Can't store this object

        var total = this.size + size;

        // Check for existing entry, as replacing it will free up space
        if (typeof(this.cache[key]) !== 'undefined') {
            for (var i = 0; i < this.order.length; ++i) {
                var entry = this.order[i];
                if (entry.key === key) {
                    total -= entry.size;
                    this.order.splice(i, 1);
                    break;
                }
            }
        }

        while (total > this.maxSize) {
            var entry = this.order.shift();
            delete this.cache[entry.key];
            total -= entry.size;
        }

        this.cache[key] = object;
        this.order.push({ size: size, key: key });
        this.size = total;
    },

    get: function(key) {
        var value = this.cache[key];
        if (typeof(value) !== 'undefined') { // Return this key for longer
            for (var i = 0; i < this.order.length; ++i) {
                var entry = this.order[i];
                if (entry.key === key) {
                    this.order.splice(i, 1);
                    this.order.push(entry);
                    break;
                }
            }
        }
        return value;
    },

    getObjectSize: function(object) {
        // Code from above estimating functions
    },
};

C'est un exemple simpliste et peut contenir des erreurs, mais il donne l'idée, car vous pouvez l'utiliser pour conserver des objets statiques (le contenu ne changera pas) avec un certain degré d'intelligence. Cela peut réduire considérablement les exigences de traitement coûteuses que l'objet devait être produit en premier lieu.

Haravikk
la source
1
function sizeOf(parent_data, size)
{
    for (var prop in parent_data)
    {
        let value = parent_data[prop];

        if (typeof value === 'boolean')
        {
            size += 4;
        }
        else if (typeof value === 'string')
        {
            size += value.length * 2;
        }
        else if (typeof value === 'number')
        {
             size += 8;
        }
        else
        {      
            let oldSize = size;
            size += sizeOf(value, oldSize) - oldSize;
        }
    }

    return size;
}


function roughSizeOfObject(object)
{   
    let size = 0;
    for each (let prop in object)
    {    
        size += sizeOf(prop, 0);
    } // for..
    return size;
}
Boris Rayskiy
la source
1

J'utilise l' onglet Chronologie des outils de développement Chrome , instancie de plus en plus de grandes quantités d'objets et obtient de bonnes estimations comme ça. Vous pouvez utiliser du HTML comme celui-ci ci-dessous, comme passe-partout, et le modifier pour mieux simuler les caractéristiques de vos objets (nombre et types de propriétés, etc ...). Vous souhaiterez peut-être cliquer sur l'icône de corbeille en bas de cet onglet d'outils de développement, avant et après une exécution.

<html>
<script>
var size = 1000*100
window.onload = function() {
  document.getElementById("quantifier").value = size
}

function scaffold()
{
  console.log("processing Scaffold...");
  a = new Array
}

function start()
{
  size = document.getElementById("quantifier").value
  console.log("Starting... quantifier is " + size);
  console.log("starting test")
  for (i=0; i<size; i++){
    a[i]={"some" : "thing"}
  }
  console.log("done...")
}

function tearDown()
{
  console.log("processing teardown");
  a.length=0
}

</script>
<body>
    <span style="color:green;">Quantifier:</span>
    <input id="quantifier" style="color:green;" type="text"></input>
    <button onclick="scaffold()">Scaffold</button>
    <button onclick="start()">Start</button>
    <button onclick="tearDown()">Clean</button>
    <br/>
</body>
</html>

L'instanciation de 2 millions d'objets d'une seule propriété chacun (comme dans ce code ci-dessus) conduit à un calcul approximatif de 50 octets par objet, sur mon Chrome, en ce moment. Changer le code pour créer une chaîne aléatoire par objet ajoute environ 30 octets par objet, etc. J'espère que cela vous aidera.

matanster
la source
-3

Je crois que vous avez oublié d'inclure «tableau».

  typeOf : function(value) {
        var s = typeof value;
        if (s === 'object')
        {
            if (value)
            {
                if (typeof value.length === 'number' && !(value.propertyIsEnumerable('length')) && typeof value.splice === 'function')
                {
                    s = 'array';
                }
            }
            else
            {
                s = 'null';
            }
        }
        return s;
    },

   estimateSizeOfObject: function(value, level)
    {
        if(undefined === level)
            level = 0;

        var bytes = 0;

        if ('boolean' === typeOf(value))
            bytes = 4;
        else if ('string' === typeOf(value))
            bytes = value.length * 2;
        else if ('number' === typeOf(value))
            bytes = 8;
        else if ('object' === typeOf(value) || 'array' === typeOf(value))
        {
            for(var i in value)
            {
                bytes += i.length * 2;
                bytes+= 8; // an assumed existence overhead
                bytes+= estimateSizeOfObject(value[i], 1)
            }
        }
        return bytes;
    },

   formatByteSize : function(bytes)
    {
        if (bytes < 1024)
            return bytes + " bytes";
        else
        {
            var floatNum = bytes/1024;
            return floatNum.toFixed(2) + " kb";
        }
    },
fchas15
la source
1
En JS, un tableau est un objet. Il peut y avoir des optimisations dans les implémentations, mais les tableaux et les objets sont identiques sur le plan conceptuel.
Kris Walker
-8

Je sais que ce n'est absolument pas la bonne façon de le faire, mais cela m'a aidé à plusieurs reprises dans le passé à obtenir la taille approximative du fichier objet:

Écrivez votre objet / réponse dans la console ou un nouvel onglet, copiez les résultats dans un nouveau fichier de bloc-notes, enregistrez-le et vérifiez la taille du fichier. Le fichier du bloc-notes lui-même ne fait que quelques octets, vous obtiendrez donc une taille de fichier objet assez précise.

Jeffrey Roosendaal
la source
4
C'est complètement faux. Par exemple, considérons le numéro 1/3 = 0,3333333333333333. Ce sera 18 octets en utilisant votre approche.
korCZis
2
J'ai dit que c'était approximatif . Parfois, vous ne vous souciez pas si c'est 1 Mo ou 1,00001 Mo, vous voulez juste connaître une estimation, alors cette méthode est parfaitement bien.
Jeffrey Roosendaal
Cheeky solution X]
Lapys