Est-il possible de définir l'attribut par défaut d'un objet javascript tel que:
var emptyObj = {};
// do some magic
emptyObj.nonExistingAttribute // => defaultValue
IE peut être ignoré, Chrome Frame m'a soulagé de ce mal de tête.
Depuis que j'ai posé la question il y a plusieurs années, les choses ont bien progressé.
Les procurations font partie de ES6. L'exemple suivant fonctionne dans Chrome, Firefox, Safari et Edge :
var handler = {
get: function(target, name) {
return target.hasOwnProperty(name) ? target[name] : 42;
}
};
var p = new Proxy({}, handler);
p.answerToTheUltimateQuestionOfLife; //=> 42
En savoir plus dans la documentation de Mozilla sur les procurations .
Il n’existe pas de moyen de définir cela en Javascript - renvoyer undefined
pour des propriétés inexistantes fait partie de la spécification JavaScript de base. Voir la discussion pour cette question similaire . Comme je l’ai suggéré, une approche (bien que je ne puisse pas vraiment le recommander) consisterait à définir une fonction globale getProperty
:
function getProperty(o, prop) {
if (o[prop] !== undefined) return o[prop];
else return "my default";
}
var o = {
foo: 1
};
getProperty(o, 'foo'); // 1
getProperty(o, 'bar'); // "my default"
Mais cela conduirait à une série de codes non standard qui seraient difficiles à lire, et cela pourrait avoir des conséquences inattendues dans des domaines où vous vous attendriez à une valeur non définie Mieux vaut vérifier au fur et à mesure:
var someVar = o.someVar || "my default";
Utilisez déstructuration (nouveauté de ES6)
Il y a beaucoup de documentation de Mozila ainsi qu'un fantastique article de blog qui explique la syntaxe mieux que moi.
var emptyObj = {};
const { nonExistingAttribute = defaultValue } = emptyObj;
console.log(nonExistingAttribute); // defaultValue
Puis-je renommer cette variable? Sûr!
const { nonExistingAttribute: coolerName = 15} = emptyObj;
console.log(coolerName); // 15
Qu'en est-il des données imbriquées? L'amener sur!
var nestedData = {
name: 'Awesome Programmer',
languages: [
{
name: 'javascript',
proficiency: 4,
}
],
country: 'Canada',
};
var {name: realName, languages: [{name: languageName}]} = nestedData ;
console.log(realName); // Awesome Programmer
console.log(languageName); // javascript
mon code est:
function(s){
s = {
top: s.top || 100, // default value or s.top
left: s.left || 300, // default value or s.left
}
alert(s.top)
}
Cela ressemble certainement à l’utilisation typique d’objets prototypes:
// define a new type of object
var foo = function() {};
// define a default attribute and value that all objects of this type will have
foo.prototype.attribute1 = "defaultValue1";
// create a new object of my type
var emptyObj = new foo();
console.log(emptyObj.attribute1); // outputs defaultValue1
Ou tu peux essayer ça
dict = {
'somekey': 'somevalue'
};
val = dict['anotherkey'] || 'anotherval';
J'ai vu un article hier qui mentionne une propriété Object.__noSuchMethod__
: JavascriptTips Je n'ai pas eu l'occasion de jouer avec elle, alors je ne connais pas le support du navigateur, mais vous pourriez peut-être l'utiliser d'une manière ou d'une autre?
Je parviens à cela avec la fonction object.assign
const defaultProperties = { 'foo': 'bar', 'bar': 'foo' }
const overwriteProperties = { 'foo': 'foo' }
const newObj = Object.assign(defaultProperties, overwriteProperties) // { 'foo': 'foo', 'bar': 'foo' }
Je suis surpris que personne n'ait encore mentionné l'opérateur ternaire.
var emptyObj = {a:'123', b:'234', c:0};
var defaultValue = 'defaultValue';
var attr = 'someNonExistAttribute';
emptyObj.hasOwnProperty(attr) ? emptyObj[attr] : defaultValue;//=> 'defaultValue'
attr = 'c'; // => 'c'
emptyObj.hasOwnProperty(attr) ? emptyObj[attr] : defaultValue; // => 0
De cette manière, même si la valeur de 'c' est 0, la valeur correcte sera toujours obtenue.
La solution la plus simple:
dict = {'first': 1,
'second': 2,
'third': 3}
À présent,
dict['last'] || 'Excluded'
retournera 'Exclus', qui est la valeur par défaut.
Je pense que l'approche la plus simple utilise Object.assign
.
Si vous avez cette classe:
class MyHelper {
constructor(options) {
this.options = Object.assign({
name: "John",
surname: "Doe",
birthDate: "1980-08-08"
}, options);
}
}
Vous pouvez l'utiliser comme ceci:
let helper = new MyHelper({ name: "Mark" });
console.log(helper.options.surname); // this will output "Doe"
Documentation (avec polyfill): https://developer.mozilla.org/it/docs/Web/JavaScript/Reference/Global_Objects/Object/assign
C'est effectivement possible avec Object.create
. Cela ne fonctionnera pas pour les propriétés "non définies". Mais pour ceux qui ont reçu une valeur par défaut.
var defaults = {
a: 'test1',
b: 'test2'
};
Ensuite, lorsque vous créez votre objet de propriétés, vous le faites avec Object.create
properties = Object.create(defaults);
Maintenant, vous aurez deux objets où le premier objet est vide, mais le prototype pointe vers l'objet defaults
Tester:
console.log('Unchanged', properties);
properties.a = 'updated';
console.log('Updated', properties);
console.log('Defaults', Object.getPrototypeOf(properties));
Object.withDefault = (defaultValue,o={}) => {
return new Proxy(o, {
get: (o, k) => (k in o) ? o[k] : defaultValue
});
}
o = Object.withDefault(42);
o.x //=> 42
o.x = 10
o.x //=> 10
o.xx //=> 42
Je suis venu ici à la recherche d'une solution car l'en-tête correspond à la description de mon problème, mais ce n'est pas ce que je cherchais mais j'ai une solution à mon problème (je voulais avoir une valeur par défaut pour un attribut qui serait dynamique comme la date ).
let Blog = {
title : String,
image : String,
body : String,
created: {type: Date, default: Date.now}
}
Le code ci-dessus était la solution pour laquelle je me suis finalement installé.
Une approche serait de prendre un objet par défaut et de le fusionner avec l'objet cible. L'objet cible remplacerait les valeurs de l'objet par défaut.
jQuery a la méthode .extend()
qui le fait. jQuery n'est pas nécessaire cependant, car il existe des implémentations de Vanilla JS telles que celles-ci peuvent être trouvées ici:
http://gomakethings.com/Vanilla-javascript-version-of-jquery-extend/