Difference between [][[]] and [[]][] in JavaScript? - javascript

The result of [ ][[ ]] is undefined
where as this [[ ]][ ] throws SyntaxError: Unexpected token ].
Any Explanation?

The object[key] syntax is used to get the property of the object by the key, which must have key inside [] otherwise there will be syntax error.
[][[]], the object is an empty array [], and the key is another empty array [].
[[]][], the object is an array with an empty array inside it, while there is no key inside [].

[] defines an empty array, so [][[]] could be rewritten as:
var a = [];
var b = [];
var c = a[b];
Now accessing an array by index where the index itself is an array is undefined - the standard doesn't say what should happen, but it's syntactically valid.
However [[]][] is broken - the closest this can be written longhand is:
var a = [];
var b = [];
[b]a;
...which is nonsense code.

I can't see why anyone would ever want to use something like this, but here is an explanation:
Case 1:
[] is an empty array. By adding [n] to it ([][n]), you reference the n-th element. n in your case is []. The interpreter tries to convert that to a usable value and ends up with an empty string (""). So you actually try to reference [][""] which is undefined.
Case 2:
[[]] is an empty array inside an empty array. By adding [n] to it ([[]][n]), you reference the n-th element of the outer array. You need to provide the index n, otherwise it throws an error, which happens in your case.

I can't imagine why you would need to use this, but here is my explanation:
[[]] is new Array( new Array()), which is an array with ONE element, an empty array.
[] is an empty array, so you can do [][2], or [][0] and it returns undefined. The second [] is the index.
So in [] [[]] you are looking for an index, the index [].
[][0] == [][[]]
But in [[]] [] the index is empty, is equivalent to [1,2,3][] -> SyntaxError: Unexpected token ]

ok. simply you should access array with a key. else it will throw syntax error.
[][[]] - array defined and you are accessing key [] from that array which is undefined.
[[]][] - array defined and you are not passing any key to access from that array - syntax error.

I guess a type conversion occurs :
[][
// an index is expected here
[] // so javascript probably tries to get a number from this empty array
]
This might be equivalent to :
[][+[]] // +[] gives 0
While in this pattern [[]][] two arrays are declared side by side.

A JavaScript object has properties associated with it. You access the properties of an object with a simple dot-notation or bracket notation, and if non existing key refered it gives undefined value.
var obj = {};
obj[ 'key' ]
and one important thing is that in JavaScript array is a Object
console.log( [] instanceof Object ) // gives true so it act like object
and funny thing is that we pass like below .
var keyCanbeFunction = function(){};
var keyCanbeObject = {};
var keyCanbeArray = [] ;
console.log( obj[ keyCanbeArray ] ) // gives undefined, that key not exists
and 1 st case :
var obj = [];
obj[ keyCanbeArray ] // gives undefined
and 2nd case :
var obj = [[ ]]
obj[]; // where is key ???

Related

How does destructuring assignment evaluate the result in my case?

I have following javascript code,
op = [
{busiCode:"001",
busiName:"Order"
},
{busiCode:"002",
busiName:"Plan"
}
]
const [{ busiCode = '' } = {}] = op
console.log(busiCode)
It prints 001, I would ask how javascript evaluate the reuslt in the above code,
Thanks!
The source value is an array. Thus, in the const declaration, the first [ says "look inside the array"
const [ // plz look in array
Then, in the source, the elements of the array (well, the first one at least), are objects. Thus in the declaration the first { means "in the first element of the array, treat it as an object and look inside".
const [{ // plz look in object at array[0]
Then, the identifier busiCode says that you want it to look for a property called "busiCode" in the object in the array, and that you want a local constant with that name ("busiCode") and the value of that property in that first object in the array.
const [{ busiCode // plz get "busiCode" property
Then the = '' means "if you can't find busiCode as a property just give me an empty string".
const [{ busiCode = '' // default to empty string if not found
Then the object "lookup" part is completed with }, and = {} means that if the original array has no first element, do all that stuff with a dummy empty object".
const [{ busiCode = '' } = {} // give me at least an empty string
The pattern of the left side of the destructuring matches the general "shape" of the right-hand side.

Can someone explain me why we used curly braces "{}" in this code?

While I was trying to check how many times an element used in an array, I found this code. It is written by another user and I got it to work but I am trying to figure out why he used "{}" at the end. I know that .reduce() method can get initialValue but I could not understand the use of braces.
var a = ["a","b","b","c","a","b","d"];
var map = a.reduce(function(obj, b) { obj[b] = ++obj[b] || 1;
return obj;
}, {});
I thought that they might be the initialValue parameter since it covers the result, but when I tried to remove the braces the result was not the same. I also checked the MDN documents, found some similar code but could not wrap my mind around it since I am quite new in JavaScript.
When we use the braces I get :
{
a: 2,
b: 3,
c: 1,
d: 1
}
But when I remove the braces and run it I get:
a
I tried using brackets and it resulted as : [ a: 2, b: 3, c: 1, d: 1 ],
So it seems the braces enclose the values but shouldn't it work as usual without braces?
But when I remove the braces and run it, I get: a
This is the syntax:
arr.reduce(callback[, initialValue])
initialValue : Value to use as the first argument to the first call of the callback. If no initial value is supplied, the first element in the array will be used."
So, if you use reduce without the initialValue({}), the first item in the array will be used as the initialValue which is "a"
So, it becomes similar to:
var a = ["a", "b", "b", "c", "a", "b", "d"];
var map = a.slice(1).reduce(function(obj, b) {
obj[b] = ++obj[b] || 1;
return obj;
}, "a");
console.log(map)
In the first iteration,
obj[b] = ++obj[b] || 1;
becomes
"a"["b"] = ++"a"["b"] || 1
This neither throws an exception, nor does it change the obj string. obj is still "a" and it will be returned every time.
The braces {} represent a new empty object in javascript, In your case, it will be the object returned by the reduce method to the map variable, we need to initialize it first then fill it in the core of the reduce callback.
Value to use as the first argument to the first call of the callback. If no initial value is supplied, the first element in the array will be used. Calling reduce() on an empty array without an initial value is an error.
It's the initialValue take a look to reduce(), here's a sample, If you were to provide an initial value as the second argument to reduce(), the result would look like this:
let arr = [0, 1, 2, 3, 4];
arr = arr.reduce((accumulator, currentValue, currentIndex, array) => {
return accumulator + currentValue;
}, 10);
console.log(arr);
That is the accumulator object.You can say that it is the initial value so when the call back function will be executed the initial value will be a empty object.
So in the example below initially it is passing an object which have key e
var a = ["a", "b", "b", "c", "a", "b", "d"];
var map = a.reduce(function(obj, b) {
console.log(obj)
obj[b] = ++obj[b] || 1;
return obj;
}, {e:'test'});
console.log(map)
The second argument in the .reduce() method is the initialValue, which is a
Value to use as the first argument to the first call of the callback. If no initial value is supplied, the first element in the array will be used.
tl;dr
It's the initial value which .reduce() starts with. This is the first argument passed to the callback in the first call.
In your case the idea was to build a map of values from the array where keys in the map were the values from the array and values in the map were a number of occurrences of that value in the array.
A map in JS can be easily simulated by an object which in your case has been passed as a literal {} to the .reduce() method. The method fires the callback for each element in the array passing the result object as the first argument and the current element in the array as the second. But the problem is at the first call - what value should be used as the result object if there were no previous elements in the array to accumulate? That's why you need to pass some initial value to have something to start with. As the MDN states, if no initialValue is passed, the first element of the array is used - that's why you got a when removed initial value. When you passed [] you told JS to have an array literal as the initial value but in the callback, you treat it as an object which is allowed in JS since an array is also an object. The problem arises when you try to iterate over those properties or stringify them using JSON.stringify(). But it's for another story ;)
{} create new object if you don't add this then the first element in the array will be used.
You can see that when you run the code with {} you get an empty object as the initialValue and fulfills your requirement.
var a = ["a","b","b","c","a","b","d"];
var map = a.reduce(function(obj, b) {
"use strict";
if (Object.entries(obj).length === 0 && obj.constructor === Object) {
console.log("InitialValue is defined as object: ", obj);
}
obj[b] = ++obj[b] || 1;
return obj;
}, {});
console.log(map);
Whereas without {} it assigns the first value of array a to the obj that means now obj is a string and when you try to use it as an object then it throws error as in the below code.
var a = ["a","b","b","c","a","b","d"];
var map = a.reduce(function(obj, b) {
"use strict";
console.log("InitialValue not defined: ", obj);
obj[b] = ++obj[b] || 1;
return obj;
});
console.log(map);
I have just added "use strict" to show this error.

chineseFood[array[0]] = array[array.length-1];

I don't understand the purpose of this = sign on the sixth line in the code block below. I understand how the argument grabs each index number of the array, I just don't understand why chineseFood[array[0]] = array[array.length-1]; In other words, I don't get the purpose of the equal sign as if it were almost comparing each other to be stored in the empty object that is stored in the variable chineseFood. Could someone please clarify? It would be much appreciated.
function transformFirstAndLast(array) {
var chineseFood = {};
//takes 1st element (at index 0) and sets it to the last element (nth index): array(length-1)
chineseFood[array[0]] = array[array.length - 1];
return chineseFood;
}
console.log( transformFirstAndLast(['Orange', 'Lemon', 'Pork', 'Chicken']) );
Output Below
{Orange: "Chicken"}
The equals sign is not comparison, it is assignment. chineseFood is an object, which means that it can be treated like a dictionary, and its properties can be accessed using the [] operator instead of the . operator:
myObj = {
foo: "bar"
};
console.log(myObj["foo"]); // bar
console.log(myObj.foo); // bar
Likewise, you can also assign properties this way:
myObj = {};
myObj["foo"] = 3;
console.log(myObj["foo"]); // 3
console.log(myObj.foo); // 3
This is what your code is doing. It is retrieving the value of array[array.length-1], which is "Chicken". Then it is assigning this value to the property of chineseFood that has the name represented by array[0], which happens to be "Orange". Thus, the property named Orange on chineseFood is set to array[array.length - 1], which is why chineseFood evaluates to {Orange: "Chicken"}.
This method of accessing properties is especially useful when you don't know the name of the property you will be changing in advance, as is the case with this code, or when you want to create properties that have names that would otherwise be illegal:
myObj = {
".you can't usually use with spaces or start w/ periods": false
};
myObj[".you can't usually use with spaces or start w/ periods"] = true;
console.log(myObj[".you can't usually use with spaces or start w/ periods"]);
// there is no way to read this property the normal way
Basically what is does is:
your object is :
var obj = {Orange: "Chicken"};
And Your array is :
var arr = ['Orange','Lemon','Pork','Chicken']
What this line says is pick first element of the array and check for this prop in object and change its value to last element of array, here:
arr[0] = "orange";
So this line :
obj[arr[0]] can be seen as obj['orange'].
After that you change its value:
Obj[arr[0]] = arr[arr.length-1] which can be written as obj['orange'] = 'chicken'

Javascript reserved word and object

I'm making a dictionary of words, so there are 1,000,000+ words.
The problem comes when I need to store the word constructor. I know this is a reserved word in javascript, but I need to add it to the dictionary.
var dictionary = {}
console.log(dictionary ['word_1'])
//undefined, this is good
console.log(dictionary ['word_2'])
//undefined, this is good
console.log(dictionary ['constructor'])
//[Function: Object]
// this cause initialization code to break
How can I fix this? I could muck with the it like key=key+"_" but that seems bad. Is there anything else I can do?
Instead of using a JS object, you could use the built-in Map type which uses strings/symbols as keys and does not conflict with any existing properties.
Replace
var dictionary = {} with var dictionary = new Map()
Override the constructor key as undefined
According to the MDN Object.prototype page, the only thing that isn't hidden by the __fieldname__ schema is the "constructor field". Thus, you could just initialize your objects via { 'constructor': undefined }.
However, you would have to make sure that in your for .. in statements would filter out all keys with undefined as their value, as it would pick up constructor as a "valid" key (even though it wouldn't before you specifically set it to undefined). I.E.
for(var key in obj) if(obj[key] !== undefined) { /* do things */ }
Check for types when getting/setting
Otherwise, you could just check the type when you 'fetch' or 'store' it. I.E.
function get(obj, key) {
if(typeof obj[key] !== 'function') // optionally, `&& typeof obj[key] !== 'object')`
return obj[key];
else
return undefined;
}
I think you should store all words and translation of them in an array. When you need to translate a word, you can use find method of Array.
For example:
var dict = [
{ word: "abc", translated: "xyz" },
...
];
Then:
var searching_word = "abc";
var translation = dict.find(function (item) {
return item.word == searching_word;
});
console.log(translation.translated);
// --> xyz
To achieve expected result , use below option of using index to get value of any key value
var dictionary = {};
var dictionary1 = {
constructor: "test"
};
//simple function to get key value using index
function getVal(obj, val) {
var keys = Object.keys(obj);
var index = keys.indexOf(val);//get index of key, in our case -contructor
return obj[keys[index]]; // return value using indec of that key
}
console.log(getVal(dictionary, "constructor"));//undefined as expected
console.log(getVal(dictionary1, "constructor"));//test
console.log(dictionary["word_1"]);
//undefined, this is good
console.log(dictionary["word_2"]);
//undefined, this is good
codepen - https://codepen.io/nagasai/pen/LOEGxM
For testing , I gave one object with key-constructor and other object without constructor.
Basically I am getting the index of key first and getting value using index

What is [keys[i]] in Javascript?

I'm reading the book Understanding EMCAScript 6 and I came across a strange line that I can't decipher. result[keys[i]] = object[keys[i]];
I know that ...keys is a rest parameter. However I can access a rest parameter using standard array syntax, for example keys[i]. What does [keys[i]] mean? I googled and I can't find anything. It looks like an array but I'm not sure what type of array or how it works. Just knowing the name would be a huge help. It's from this code.
function pick(object, ...keys) {
let result = Object.create(null);
for (let i = 0, len = keys.length; i < len; i++) {
result[keys[i]] = object[keys[i]];
}
return result;
}
It's no magic, just nested property access using bracket notation.
result[ keys[i] ] = object[ keys[i] ];
could also be written
const key = keys[i];
result[key] = object[key];
To understand this function, you have to understand that, in JavaScript objects are just hashes. object.foo is just syntactic sugar for object["foo"].
This means that you can dynamically get and set object properties, which is what this function is doing.
The keys value is an array of the arguments passed to the function. Therefore, the for loop iterates over every value in keys.
The expression keys[i] means ith element of keys.
The expression object[key] means the property of the object named key. For example, if key = "foo", then writing object[key] is the same as writing object.foo.
This means that the for loop in the function:
Looks up the object property matching the given argument;
Creates a new property in result with the same name, and assigns the value of the property to it
Therefore, the pick function can be used to select certain attributes from an object:
pick({x: 1, y: 2, z: 3}, "x", "z") // -> {x: 1, z: 3}

Categories

Resources