Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.javascript > #38386 > unrolled thread

check for obj nested prop

Started byAndrew Poulos <ap_prog@hotmail.com>
First post2020-05-08 15:37 +1000
Last post2020-05-13 12:30 -0700
Articles 17 — 8 participants

Back to article view | Back to comp.lang.javascript


Contents

  check for obj nested prop Andrew Poulos <ap_prog@hotmail.com> - 2020-05-08 15:37 +1000
    Re: check for obj nested prop Ben Bacarisse <ben.usenet@bsb.me.uk> - 2020-05-08 10:52 +0100
      Re: check for obj nested prop Thomas 'PointedEars' Lahn <PointedEars@web.de> - 2020-05-09 00:26 +0200
        Re: check for obj nested prop Ben Bacarisse <ben.usenet@bsb.me.uk> - 2020-05-09 03:09 +0100
          Re: check for obj nested prop Thomas 'PointedEars' Lahn <PointedEars@web.de> - 2020-05-12 09:28 +0200
            Re: check for obj nested prop Julio Di Egidio <julio@diegidio.name> - 2020-05-12 04:01 -0700
      Exception handling (was: check for obj nested prop) Thomas 'PointedEars' Lahn <PointedEars@web.de> - 2020-05-09 03:46 +0200
    Re: check for obj nested prop JJ <jj4public@vfemail.net> - 2020-05-08 17:18 +0700
    Re: check for obj nested prop Julio Di Egidio <julio@diegidio.name> - 2020-05-08 03:53 -0700
    Re: check for obj nested prop James Kirk <noneya.invalid@gmail.com> - 2020-05-08 11:00 -0400
    Re: check for obj nested prop Thomas 'PointedEars' Lahn <PointedEars@web.de> - 2020-05-09 00:19 +0200
      Re: check for obj nested prop Julio Di Egidio <julio@diegidio.name> - 2020-05-12 04:04 -0700
        Re: check for obj nested prop luserdroog <luser.droog@gmail.com> - 2020-05-12 07:59 -0700
    Re: check for obj nested prop "Michael Haufe (TNO)" <tno@thenewobjective.com> - 2020-05-12 14:17 -0700
      Re: check for obj nested prop Thomas 'PointedEars' Lahn <PointedEars@web.de> - 2020-05-13 02:46 +0200
      Re: check for obj nested prop Andrew Poulos <ap_prog@hotmail.com> - 2020-05-13 13:08 +1000
        Re: check for obj nested prop "Michael Haufe (TNO)" <tno@thenewobjective.com> - 2020-05-13 12:30 -0700

#38386 — check for obj nested prop

FromAndrew Poulos <ap_prog@hotmail.com>
Date2020-05-08 15:37 +1000
Subjectcheck for obj nested prop
Message-ID<C9udnTlJHfCQbSnDnZ2dnUU7-U3NnZ2d@westnet.com.au>
If I have an object and it get properties added dynamically when I need 
to test for a "nested" property and one of the "ascendant" properties 
doesn't exist I get an error. For example,

let obj = {a: 1};
if (a.b.c.d) // throws error

so I end up doing

if (a && a.b && a.b.c && a.b.c.d)

What happens is that every now and then I get caught when I assume the 
properties should exist.

Is there a way to get the check value of an object's nested property 
without first having to test for all the ascendant properties?

Andrew Poulos

[toc] | [next] | [standalone]


#38387

FromBen Bacarisse <ben.usenet@bsb.me.uk>
Date2020-05-08 10:52 +0100
Message-ID<87pnbeycrm.fsf@bsb.me.uk>
In reply to#38386
Andrew Poulos <ap_prog@hotmail.com> writes:

> let obj = {a: 1};
> if (a.b.c.d) // throws error

Did you mean if (obj.a.b.c.d) ?

> so I end up doing
>
> if (a && a.b && a.b.c && a.b.c.d)
<cut>
> Is there a way to get the check value of an object's nested property
> without first having to test for all the ascendant properties?

  if (try {obj.a.b.c.d} catch {})

might do what you want.

-- 
Ben.

[toc] | [prev] | [next] | [standalone]


#38392

FromThomas 'PointedEars' Lahn <PointedEars@web.de>
Date2020-05-09 00:26 +0200
Message-ID<11518358.O9o76ZdvQC@PointedEars.de>
In reply to#38387
Ben Bacarisse wrote:

> Andrew Poulos <ap_prog@hotmail.com> writes:
>> so I end up doing
>>
>> if (a && a.b && a.b.c && a.b.c.d)
> <cut>
>> Is there a way to get the check value of an object's nested property
>> without first having to test for all the ascendant properties?
> 
>   if (try {obj.a.b.c.d} catch {})
> 
> might do what you want.

This is *obviously* syntactically invalid; “try {obj.a.b.c.d} catch {}” is 
not an /Assignment*Expression*/, but a /Try*Statement*/.  If you do not want 
to learn the grammar of the languages, please at least do minimal testing 
before you post suggestions.

<http://ecma-international.org/ecma-262/#prod-IfStatement>

-- 
PointedEars
FAQ: <http://PointedEars.de/faq> | <http://PointedEars.de/es-matrix>
<https://github.com/PointedEars> | <http://PointedEars.de/wsvn/>
Twitter: @PointedEars2 | Please do not cc me./Bitte keine Kopien per E-Mail.

[toc] | [prev] | [next] | [standalone]


#38394

FromBen Bacarisse <ben.usenet@bsb.me.uk>
Date2020-05-09 03:09 +0100
Message-ID<873689yi4j.fsf@bsb.me.uk>
In reply to#38392
Thomas 'PointedEars' Lahn <PointedEars@web.de> writes:

> Ben Bacarisse wrote:
>
>> Andrew Poulos <ap_prog@hotmail.com> writes:
>>> so I end up doing
>>>
>>> if (a && a.b && a.b.c && a.b.c.d)
>> <cut>
>>> Is there a way to get the check value of an object's nested property
>>> without first having to test for all the ascendant properties?
>> 
>>   if (try {obj.a.b.c.d} catch {})
>> 
>> might do what you want.
>
> This is *obviously* syntactically invalid;

Yes, wishful thinking.  You'd need a function call and a return:

  if ( (()=>{ try {return obj.a.b.c.d} catch {} })() ) ...

which makes it rather clumsy.

-- 
Ben.

[toc] | [prev] | [next] | [standalone]


#38401

FromThomas 'PointedEars' Lahn <PointedEars@web.de>
Date2020-05-12 09:28 +0200
Message-ID<2559382.mvXUDI8C0e@PointedEars.de>
In reply to#38394
Ben Bacarisse wrote:

> Thomas 'PointedEars' Lahn <PointedEars@web.de> writes:
>> Ben Bacarisse wrote:
>>> Andrew Poulos <ap_prog@hotmail.com> writes:
>>>> so I end up doing
>>>>
>>>> if (a && a.b && a.b.c && a.b.c.d)
>>> <cut>
>>>> Is there a way to get the check value of an object's nested property
>>>> without first having to test for all the ascendant properties?
>>> 
>>>   if (try {obj.a.b.c.d} catch {})
>>> 
>>> might do what you want.
>>
>> This is *obviously* syntactically invalid;
> 
> Yes, wishful thinking.  You'd need a function call and a return:
> 
>   if ( (()=>{ try {return obj.a.b.c.d} catch {} })() ) ...
> 
> which makes it rather clumsy.

It is not only clumsy, it is also not safe (and this particular syntax
is also not backwards-compatible; the compatible syntax is even more 
clumsy); see my *detailed* follow-up.
 
-- 
PointedEars
FAQ: <http://PointedEars.de/faq> | <http://PointedEars.de/es-matrix>
<https://github.com/PointedEars> | <http://PointedEars.de/wsvn/>
Twitter: @PointedEars2 | Please do not cc me./Bitte keine Kopien per E-Mail.

[toc] | [prev] | [next] | [standalone]


#38402

FromJulio Di Egidio <julio@diegidio.name>
Date2020-05-12 04:01 -0700
Message-ID<a9582e21-4ae2-43d4-b6d1-dc6a4db1ca6e@googlegroups.com>
In reply to#38401
On Tuesday, 12 May 2020 09:28:37 UTC+2, Thomas 'PointedEars' Lahn  wrote:
> Ben Bacarisse wrote:
> 
> > Thomas 'PointedEars' Lahn <PointedEars@web.de> writes:
> >> Ben Bacarisse wrote:
> >>> Andrew Poulos <ap_prog@hotmail.com> writes:
> >>>> so I end up doing
> >>>>
> >>>> if (a && a.b && a.b.c && a.b.c.d)
> >>> <cut>
> >>>> Is there a way to get the check value of an object's nested property
> >>>> without first having to test for all the ascendant properties?
> >>> 
> >>>   if (try {obj.a.b.c.d} catch {})
> >>> 
> >>> might do what you want.
> >>
> >> This is *obviously* syntactically invalid;
> > 
> > Yes, wishful thinking.  You'd need a function call and a return:
> > 
> >   if ( (()=>{ try {return obj.a.b.c.d} catch {} })() ) ...
> > 
> > which makes it rather clumsy.
> 
> It is not only clumsy, it is also not safe (and this particular syntax
> is also not backwards-compatible; the compatible syntax is even more 
> clumsy); see my *detailed* follow-up.

You insist on syntactic minutiae while missing the one substantial point:
raising exceptions to do flow control is a no no!

Julio

[toc] | [prev] | [next] | [standalone]


#38393 — Exception handling (was: check for obj nested prop)

FromThomas 'PointedEars' Lahn <PointedEars@web.de>
Date2020-05-09 03:46 +0200
SubjectException handling (was: check for obj nested prop)
Message-ID<5599059.lOV4Wx5bFT@PointedEars.de>
In reply to#38387
Ben Bacarisse wrote:

> Andrew Poulos <ap_prog@hotmail.com> writes:
>> let obj = {a: 1};
>> if (a.b.c.d) // throws error
> 
> Did you mean if (obj.a.b.c.d) ?

Probably yes.

>> so I end up doing
>>
>> if (a && a.b && a.b.c && a.b.c.d)
> <cut>
>> Is there a way to get the check value of an object's nested property
>> without first having to test for all the ascendant properties?
> 
>   if (try {obj.a.b.c.d} catch {})
> 
> might do what you want.

By contrast, the following is syntactically correct:

  try {
    if (obj.a.b.c.d)
    {
      // …
    }
  } catch {}

However, there are several caveats:

1. The omission of the exception parameter requires an implementation of
   ECMAScript Edition 10 (ECMAScript 2019).  This is the most recent
   Edition of the standard and requires the most recent version of a runtime
   environment (e.g. a Web browser) to have a chance to be implemented.

   Compare

     <http://ecma-international.org/ecma-262/9.0/#prod-Catch>

   with

     <http://ecma-international.org/ecma-262/10.0/#prod-Catch>

2. Using an empty try-catch block can hide problems in code that are not
   syntax errors, and is strongly recommended against (as in “SHOULD NOT”). 
   For example, the code above hides a problem of an undeclared identifier
   “obj” even in strict mode, which would throw a ReferenceError exception.

   Therefore, if try-catch is used, in almost all cases exception handling
   should be specific.

   Unfortunately, ECMAScript did not standardize a feature of Mozilla
   JavaScript where it was possible to write

     catch (e if e instanceof ExceptionType) {
       // …
     }

   where ExceptionType would be the exception type, e.g. TypeError,
   and as of Mozilla JavaScript 68 (Firefox 68) it is removed from
   the implementation.

   However,

     try {
     }
     catch (e) {
       if (e instanceof ExceptionType) {
         // …
       }
     }

    is functionally equivalent and strictly standards-compliant
    (specified explicitly in the standard).

    Finally, exceptions that are not handled should be re-thrown so as to
    not hide more serious problems:
  
     catch (e) {
       if (e instanceof ExceptionType) {
         // …
       }
       else if (e instanceof …) {
         // …
       }
       else throw e;
     }

3. With that said, it is actually not easy to tell exception conditions 
   apart.  For example, if a property-read access results in the “undefined”
   value because an object does not have a property with the specified name,
   then the subsequent lookup of a “nested” property will throw a TypeError
   exception because “undefined has no properties” (it is a primitive
   value that cannot be converted to an object).

   But a TypeError exception is being thrown by several other operations as
   well (see the standard’s prose), so the recommended *alternative* code

     try {
       if (obj.a.b.c.d)
       {
         // …
       }
     } catch (e) {
       if (e instanceof TypeError) {
         // …
       }
       else throw e;
     }

   is *unable* to tell those conditions apart, and there is none more
   specific exception type, e.g. a “KeyError“ exception (as it is available
   for example in Python).

Surprising to me, the Airbnb JavaScript Style Guide¹ makes no explicit 
recommendation or requirement for exception handling.  However, they refer 
to a jsPerf test case for “Try/Catch Cost In a Loop”:

<https://jsperf.com/try-catch-in-loop-cost/12>

Also, you should be aware that while ESLint² supports defining several rules 
for “throw” and “catch”³, none of them can protect against the problems with 
exception handling that I discussed above.

______
¹ <https://github.com/airbnb/javascript>
² <https://eslint.org/>
³ <https://eslint.org/docs/rules/>
 
-- 
PointedEars
FAQ: <http://PointedEars.de/faq> | <http://PointedEars.de/es-matrix>
<https://github.com/PointedEars> | <http://PointedEars.de/wsvn/>
Twitter: @PointedEars2 | Please do not cc me./Bitte keine Kopien per E-Mail.

[toc] | [prev] | [next] | [standalone]


#38388

FromJJ <jj4public@vfemail.net>
Date2020-05-08 17:18 +0700
Message-ID<i0t71igay4zr$.11lgr72f0kf1s$.dlg@40tude.net>
In reply to#38386
On Fri, 8 May 2020 15:37:15 +1000, Andrew Poulos wrote:
> If I have an object and it get properties added dynamically when I need 
> to test for a "nested" property and one of the "ascendant" properties 
> doesn't exist I get an error. For example,
> 
> let obj = {a: 1};
> if (a.b.c.d) // throws error
> 
> so I end up doing
> 
> if (a && a.b && a.b.c && a.b.c.d)
> 
> What happens is that every now and then I get caught when I assume the 
> properties should exist.
> 
> Is there a way to get the check value of an object's nested property 
> without first having to test for all the ascendant properties?
> 
> Andrew Poulos

No. But you can create a function to simplify that. e.g.

function getProperty(obj, propPath) {
  return propPath.split(".").reduce((r, k) => r = r && r[k], obj);
}
console.clear();
let obj = {a: 1};
console.log(1, getProperty(obj, "a")); //1
console.log(2, getProperty(obj, "b")); //undefined
console.log(3, getProperty(obj, "b.c")); //undefined
obj.b = {};
console.log(4, getProperty(obj, "b")); //{}
console.log(5, getProperty(obj, "b.c")); //undefined
obj.b.c = [];
console.log(6, getProperty(obj, "b.c")); //[]

[toc] | [prev] | [next] | [standalone]


#38389

FromJulio Di Egidio <julio@diegidio.name>
Date2020-05-08 03:53 -0700
Message-ID<c009b9d6-b76c-431a-b630-445489bbbd12@googlegroups.com>
In reply to#38386
On Friday, 8 May 2020 07:37:26 UTC+2, Andrew Poulos  wrote:
> If I have an object and it get properties added dynamically when I need 
> to test for a "nested" property and one of the "ascendant" properties 
> doesn't exist I get an error. For example,
> 
> let obj = {a: 1};
> if (a.b.c.d) // throws error
> 
> so I end up doing
> 
> if (a && a.b && a.b.c && a.b.c.d)
> 
> What happens is that every now and then I get caught when I assume the 
> properties should exist.

How can you forget to check?  (If that's what you mean.)  As you describe
the situation, you have to check the whole property chain *every time* you
access a property of that object.

> Is there a way to get the check value of an object's nested property 
> without first having to test for all the ascendant properties?

Typically, no...  (typically, you would not raise exceptions to do flow
control, and you would not hard-code strings in place of static code:
typically...).

Julio

[toc] | [prev] | [next] | [standalone]


#38390

FromJames Kirk <noneya.invalid@gmail.com>
Date2020-05-08 11:00 -0400
Message-ID<20200508110012.60d3c6d4@james.kirk.invalid>
In reply to#38386
In Message: <C9udnTlJHfCQbSnDnZ2dnUU7-U3NnZ2d@westnet.com.au>
Andrew Poulos <ap_prog@hotmail.com> wrote:

> If I have an object and it get properties added dynamically when I
> need to test for a "nested" property and one of the "ascendant"
> properties doesn't exist I get an error. For example,

> let obj = {a: 1};
> if (a.b.c.d) // throws error

> so I end up doing

> if (a && a.b && a.b.c && a.b.c.d)

> What happens is that every now and then I get caught when I assume
> the properties should exist.

> Is there a way to get the check value of an object's nested
> property without first having to test for all the ascendant
> properties?

nested destructuring

let objA = {big: 'toe'},
objB = {A: {B: {C: {D: 'look at D' } } } },
{a,a:{b,b:{c,c:{d}=''}=''}=''} = objA,
{A,A:{B,B:{C,C:{D}=''}=''}=''} = objB;

console.log(a);
console.log(b);
console.log(c);
console.log(d);

console.log(A);
console.log(B);
console.log(C);
console.log(D);

-- 
James Kirk

[toc] | [prev] | [next] | [standalone]


#38391

FromThomas 'PointedEars' Lahn <PointedEars@web.de>
Date2020-05-09 00:19 +0200
Message-ID<2530230.mvXUDI8C0e@PointedEars.de>
In reply to#38386
Andrew Poulos wrote:

> If I have an object and it get properties added dynamically when I need
> to test for a "nested" property and one of the "ascendant" properties
> doesn't exist I get an error. For example,
> 
> let obj = {a: 1};
> if (a.b.c.d) // throws error
> 
> so I end up doing
> 
> if (a && a.b && a.b.c && a.b.c.d)
> 
> What happens is that every now and then I get caught when I assume the
> properties should exist.
> 
> Is there a way to get the check value of an object's nested property
> without first having to test for all the ascendant properties?

No.  Therefore I had written jsx.object.getFeature().  It has the advantage 
over the approach presented by “JJ” that it also supports property names 
that contain a “.”.  It basically differs from their approach in that you 
(can) pass multiple String values as arguments instead of a single String 
value.  (I had the one-string approach first, but ran into problems with “.” 
in property names.)

It can be used like this:

  if (_getFeature(a, 'b', 'c', 'd')) {
    // …
  }

<https://github.com/PointedEars/JSX/blob/master/object.js#L970>

-- 
PointedEars
FAQ: <http://PointedEars.de/faq> | <http://PointedEars.de/es-matrix>
<https://github.com/PointedEars> | <http://PointedEars.de/wsvn/>
Twitter: @PointedEars2 | Please do not cc me./Bitte keine Kopien per E-Mail.

[toc] | [prev] | [next] | [standalone]


#38403

FromJulio Di Egidio <julio@diegidio.name>
Date2020-05-12 04:04 -0700
Message-ID<bd26a96b-d081-4dcb-9e42-9f7c4e544cb4@googlegroups.com>
In reply to#38391
On Saturday, 9 May 2020 00:19:22 UTC+2, Thomas 'PointedEars' Lahn  wrote:
> Andrew Poulos wrote:
> 
> > If I have an object and it get properties added dynamically when I need
> > to test for a "nested" property and one of the "ascendant" properties
> > doesn't exist I get an error. For example,
> > 
> > let obj = {a: 1};
> > if (a.b.c.d) // throws error
> > 
> > so I end up doing
> > 
> > if (a && a.b && a.b.c && a.b.c.d)
> > 
> > What happens is that every now and then I get caught when I assume the
> > properties should exist.
> > 
> > Is there a way to get the check value of an object's nested property
> > without first having to test for all the ascendant properties?
> 
> No.  Therefore I had written jsx.object.getFeature().  It has the advantage 
> over the approach presented by “JJ” that it also supports property names 
> that contain a “.”.  It basically differs from their approach in that you 
> (can) pass multiple String values as arguments instead of a single String 
> value.  (I had the one-string approach first, but ran into problems with “.” 
> in property names.)
> 
> It can be used like this:
> 
>   if (_getFeature(a, 'b', 'c', 'd')) {
>     // …
>   }
> 
> <https://github.com/PointedEars/JSX/blob/master/object.js#L970>

Another "clever" solution that is highly advised against except for special
situations: in general, hard-coding strings in place of static code is another
no no...

Julio

[toc] | [prev] | [next] | [standalone]


#38404

Fromluserdroog <luser.droog@gmail.com>
Date2020-05-12 07:59 -0700
Message-ID<2830b2bf-118d-4e60-beae-c562a07d1f8c@googlegroups.com>
In reply to#38403
On Tuesday, May 12, 2020 at 6:04:49 AM UTC-5, Julio Di Egidio wrote:
> On Saturday, 9 May 2020 00:19:22 UTC+2, Thomas 'PointedEars' Lahn  wrote:
> > Andrew Poulos wrote:
> > 
> > > Is there a way to get the check value of an object's nested property
> > > without first having to test for all the ascendant properties?
> > 
> > No.  Therefore I had written jsx.object.getFeature().  It has the advantage 
> > over the approach presented by “JJ” that it also supports property names 
> > that contain a “.”.  It basically differs from their approach in that you 
> > (can) pass multiple String values as arguments instead of a single String 
> > value.  (I had the one-string approach first, but ran into problems with “.” 
> > in property names.)
> > 
> > It can be used like this:
> > 
> >   if (_getFeature(a, 'b', 'c', 'd')) {
> >     // …
> >   }
> > 
> > <https://github.com/PointedEars/JSX/blob/master/object.js#L970>
> 
> Another "clever" solution that is highly advised against except for special
> situations: in general, hard-coding strings in place of static code is another
> no no...

Do you have a list of all the no no-s? I probably do a bunch.
Single-letter variables?

[toc] | [prev] | [next] | [standalone]


#38407

From"Michael Haufe (TNO)" <tno@thenewobjective.com>
Date2020-05-12 14:17 -0700
Message-ID<70e81d39-3e56-4366-8d8a-b7366dcfb715@googlegroups.com>
In reply to#38386
On Friday, May 8, 2020 at 12:37:26 AM UTC-5, Andrew Poulos wrote:
> If I have an object and it get properties added dynamically when I need 
> to test for a "nested" property and one of the "ascendant" properties 
> doesn't exist I get an error. For example,
> 
> let obj = {a: 1};
> if (a.b.c.d) // throws error
> 
> so I end up doing
> 
> if (a && a.b && a.b.c && a.b.c.d)
> 
> What happens is that every now and then I get caught when I assume the 
> properties should exist.
> 
> Is there a way to get the check value of an object's nested property 
> without first having to test for all the ascendant properties?

In modern JavaScript Optional Chaining exists:

```js
if(obj.a?.b?.c?.d)
   ...
```

Details:

<https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Optional_chaining>

[toc] | [prev] | [next] | [standalone]


#38409

FromThomas 'PointedEars' Lahn <PointedEars@web.de>
Date2020-05-13 02:46 +0200
Message-ID<5384004.DvuYhMxLoT@PointedEars.de>
In reply to#38407
Michael Haufe (TNO) wrote:

> On Friday, May 8, 2020 at 12:37:26 AM UTC-5, Andrew Poulos wrote:
>> Is there a way to get the check value of an object's nested property
>> without first having to test for all the ascendant properties?
> 
> In modern JavaScript Optional Chaining exists:
> 
> ```js
> if(obj.a?.b?.c?.d)
>    ...
> ```
> 
> Details:
> 
> <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Optional_chaining>

Very nice, thanks.

It is also emulated by Babel (7).  For example,

  if (obj?.a) {
    foo;
  }

becomes

  var _obj;

  if ((_obj = obj) == null ? void 0 : _obj.a) {
    foo;
  }

<https://babeljs.io/>

-- 
PointedEars
FAQ: <http://PointedEars.de/faq> | <http://PointedEars.de/es-matrix>
<https://github.com/PointedEars> | <http://PointedEars.de/wsvn/>
Twitter: @PointedEars2 | Please do not cc me./Bitte keine Kopien per E-Mail.

[toc] | [prev] | [next] | [standalone]


#38410

FromAndrew Poulos <ap_prog@hotmail.com>
Date2020-05-13 13:08 +1000
Message-ID<H_CdneUVbcFZ-SbDnZ2dnUU7-SHNnZ2d@westnet.com.au>
In reply to#38407
On 13/05/2020 7:17 am, Michael Haufe (TNO) wrote:
> On Friday, May 8, 2020 at 12:37:26 AM UTC-5, Andrew Poulos wrote:
>> If I have an object and it get properties added dynamically when I need
>> to test for a "nested" property and one of the "ascendant" properties
>> doesn't exist I get an error. For example,
>>
>> let obj = {a: 1};
>> if (a.b.c.d) // throws error
>>
>> so I end up doing
>>
>> if (a && a.b && a.b.c && a.b.c.d)
>>
>> What happens is that every now and then I get caught when I assume the
>> properties should exist.
>>
>> Is there a way to get the check value of an object's nested property
>> without first having to test for all the ascendant properties?
> 
> In modern JavaScript Optional Chaining exists:
> 
> ```js
> if(obj.a?.b?.c?.d)
>     ...
> ```
> 
> Details:
> 
> <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Optional_chaining>

Just what I needed. The page mentions the "nullish coalescing operator" 
for which it gives the example
   const customerCity = customer?.city ?? "Unknown city";

I've not used that operator before. What I would've done is
   const customerCity = customer?.city || "Unknown city";

Is using the former operator "better" than the later?

Andrew Poulos

[toc] | [prev] | [next] | [standalone]


#38413

From"Michael Haufe (TNO)" <tno@thenewobjective.com>
Date2020-05-13 12:30 -0700
Message-ID<bdde63fd-8374-467b-ac76-0508a16a10bc@googlegroups.com>
In reply to#38410
On Tuesday, May 12, 2020 at 10:09:03 PM UTC-5, Andrew Poulos wrote:
>
> Just what I needed. The page mentions the "nullish coalescing operator" 
> for which it gives the example
>    const customerCity = customer?.city ?? "Unknown city";
> 
> I've not used that operator before. What I would've done is
>    const customerCity = customer?.city || "Unknown city";
> 
> Is using the former operator "better" than the later?

The (||) operator works on falsey values and the (??) operator works on null|undefined. In most cases you'll want to get in the habit of using (??) instead as you'll avoid more bugs that way. An example of a bug:

```js
let height = rectangle.height || 10
```

If `rectangle.height` is '0' then `height` would be set to `10` which is probably not your intention when you just wanted a default. Using (??) would avoid this problem:

```js
let height = rectangle.height ?? 10
```

So it's 'better' to use (??).

Philosophically I think both cases are tactically smart but strategically dumb; `null` and `undefined` should be prevented from existing in the first place:

<https://www.infoq.com/presentations/Null-References-The-Billion-Dollar-Mistake-Tony-Hoare/>

You do so by making your models (you domain) doesn't have them in the first place.

[toc] | [prev] | [standalone]


Back to top | Article view | comp.lang.javascript


csiph-web