From: Garrett Smith on
nick wrote:
> On May 10, 3:21 am, Garrett Smith <dhtmlkitc...(a)gmail.com> wrote:
>> nick wrote:
>>> What's the "best" way to determine if a variable is defined?
>
>> Depends. If conditional assignment results in an object value
>> [...] then why not use boolean conversion?
>
>> if(x) { [...]
>
> True, I guess I should have mentioned it for the sake of completeness.
> I'm really more concerned with undefined vs. not undefined ATM, but
> this would be good to include in a FAQ entry or something, along with
> 'in'.

Sure. However there is some catchall behavior that does not provide
hooks for "has". Some catchall implementations exist with host objects
such as any of the dom collections or navigator.plugins.

javascript: alert(
["Shockwave Flash" in navigator.plugins ,
navigator.plugins["Shockwave Flash"] ]);

The example code shows in Firefox 3.6 "false, [object Plugin]".

The `in` operator indicates that the plugin property does not exists yet
[[Get]] results in the desired plugin object.

>
>> Identifiers that are declared with var get DontDelete, so don't worry
>> about the case where they were deleted -- they can't be.
>
> Interesting. So deleting them just leaves their value as-is, huh?
>

Check result of calling delete.

var x;
alert(delete x); // false.

> The console in Chromium tricked me. Look at this:
>
[...]

Chrome console likely uses eval.

For eval code:
| Variable instantiation is performed using the calling context's
| variable object and using empty property attributes.

That means there is no DontDelete.

See also:
http://perfectionkills.com/understanding-delete/#firebug_confusion
http://groups.google.am/group/comp.lang.javascript/browse_thread/thread/8604c3c08794dc34#msg_cb73090b3da02eda

>> For other values, it is useful to make different checks, depending on
>> what the code needs ot know. [...]
>
> Agreed.
>
>>> function isDefined (v) { return (v !== void 0) }
>
>> That tells if a value is not undefined. The isDefined function in the
>> general sense does not provide any advantage over an inline check.
>
> That's true; If there's going to be a function call the function could
> just be a no-op (returning undefined).
>

an isXXX function should return a boolean value.

>> It does not say, in the general sense, if `v` has been declared,
>
> What do you mean? 'v' is declared as an argument to isDefined, right?
> That was sort of the point of this example.
>

The only way for isDefined to if `v` was passed in is to check
arguments.length.

>> does not say if has been assigned a value (undefined is a value), does not
>> say if `v` is a variable, a property of something, the result of trying
>> to get a property that was not available.
>
> Ok, I see what you're getting at.
>

What I am getting at is that the function removed from context tells
less than can be deduced in context. It does not differentiate any of
the cases:

var o = {};
isDefined(o.blah);
o.blah = Function.prototype();
isDefined(undefined);
var x;
isDefined(x);
x = undefined;
isDefined(x);


>> Consider that, given function scope:
>
>> (function(){
>> var undef, myVar;
>> //...
>> var isDef = isDefined(myVar);
>> var isDef2 = myVar !== undef;
>> })();
>
> Hmm, I'm not totally sold. If we're going to do it like that why not
> just shadow the global undefined and use that?
>

OK.

>> For the cost of a function call, plus organizing and managing that
>> function, it is not worth it.
>
> You are probably right. That function was not really the ultimate
> point of the OP, it was just an example of a way to check for things
> having a value of undefined (inline or otherwise) using the syntax
> that I liked the most of the three examples above.
>
> Still, I sort of like the idea of encapsulating it in a function.

What for?
--
Garrett
comp.lang.javascript FAQ: http://jibbering.com/faq/
From: Lasse Reichstein Nielsen on
nick <nick___(a)fastmail.fm> writes:

> Interesting. So deleting them just leaves their value as-is, huh?
>
> The console in Chromium tricked me. Look at this:
>
> var x=5; alert(x); delete x; alert(x);
> // alerts "5"
> // throws ReferenceError: x is not defined
>
> I figured I had successfully deleted the var. But this line acts
> totally different:
>
> (function(){var x=5; alert(x); delete x; alert(x);})()
> // alerts "5" twice
> // function returns undefined as normal
>
> Looks like there's some serious black magic being performed by the
> console in the first example.

No black magic necessary, it probably just uses a direct call to
"eval" to evaluate the input. The expected behavior of variables
created in an eval code is to make them configurable (deletable),
wheras variables in program or function code are not configurable.
(See ECMAScript 5, section 10.5).

/L 'Know thy spec'.
--
Lasse Reichstein Holst Nielsen
'Javascript frameworks is a disruptive technology'

From: Bart Lateur on
David Mark wrote:

>Bart Lateur wrote:
>> David Mark wrote:
>>
>>> If x will be either be undefined or a "truthy" value (e.g. won't be
>>> null), use boolean type conversion:-
>>>
>>> if (x) {
>>> doStuff(x);
>>> }
>>
>> Carefull: x = 0 and x = "" both produce a false, too.
>>
>
>Example given; it wasn't meant to be a complete reference of "falsey"
>values. And which did you leave out? :)

Well...

I'm wondering why in the original question

if (x == null) {
doStuff(x);
}

won't do.

--
Bart Lateur
bart.lateur(a)telenet.be
From: Thomas 'PointedEars' Lahn on
Bart Lateur wrote:

> David Mark wrote:
>> Bart Lateur wrote:
>>> David Mark wrote:
>>>> If x will be either be undefined or a "truthy" value (e.g. won't be
>>>> null), use boolean type conversion:-
>>>>
>>>> if (x) {
>>>> doStuff(x);
>>>> }
>>>
>>> Carefull: x = 0 and x = "" both produce a false, too.
>>
>> Example given; it wasn't meant to be a complete reference of "falsey"
>> values. And which did you leave out? :)
>
> Well...
>
> I'm wondering why in the original question
>
> if (x == null) {
> doStuff(x);
> }
>
> won't do.

Keep in mind that the original question was “What's the 'best' way to
determine if a variable is defined?” If "defined" is understood as "does
not throw a ReferenceError exception with message '... is not defined', then
the following applies:

If `x' was not declared a variable (and so that variable was not defined),
evaluation of your comparison would throw a ReferenceError. Not so with
`typeof', but that comes at a price: With `typeof' you cannot determine
whether the property referred to by the /Identifier/ was declared a variable
(a property of a Variable Object with the attribute DontDelete).

If `x' was declared and implicitly initialized with `undefined' --

var x;

-- or `null' --

var x = null;

-- or assigned `undefined', e.g.

var x = void 0;

-- doStuff() would be called anyway with your code as `undefined == null'
(it is a type-converting comparison).

ISTM the only way to determine whether an identifier is available is to try
and catch possible ReferenceError exceptions. And without static code
analysis there appears to be no way of determining if an identifier has been
declared a variable but that variable has not been initialized (as it may
have been explicitly initialized with `undefined' or assigned that value
after initialization, but before the test.)


PointedEars
--
Danny Goodman's books are out of date and teach practices that are
positively harmful for cross-browser scripting.
-- Richard Cornford, cljs, <cife6q$253$1$8300dec7(a)news.demon.co.uk> (2004)
From: Dr J R Stockton on
In comp.lang.javascript message <ab37b500-1b97-450c-9498-badd643ac361(a)j3
5g2000yqm.googlegroups.com>, Sun, 9 May 2010 20:02:32, nick
<nick___(a)fastmail.fm> posted:

>What's the "best" way to determine if a variable is defined?

I don't recall any problem in testing X for the value undefined by using

var U
// ...
if (X==U) ...

although one must remember not to define U. That should continue to
work even if ECMA 6 redefines the value of an undefined variable.


But, of course, for that the variable must have been defined; only its
value is, by definition, the value undefined - until it is defined.

It was a design fault to give the language an undefined type and an
undefined value, since it is then unnecessarily difficult to talk about
it in English. Instead, non-words should have been used - "taghairm"
would nearly serve; "trygdyl" would do. All who know English reasonably
well will understand that those are not English words.

One cannot test directly whether the variable 'akwidukt' has been
declared, since a simple reference to it will give an error. But
'window.akwidukt' is merely 'undefined' if 'akwidukt' has not been
defined.

--
(c) John Stockton, nr London, UK. ?@merlyn.demon.co.uk Turnpike v6.05 IE 7.
Web <URL:http://www.merlyn.demon.co.uk/> - FAQish topics, acronyms, & links.
MiniTrue is good for viewing/searching/altering files, at a DOS / CMD prompt;
free, DOS/Win/UNIX, new via <URL:http://www.merlyn.demon.co.uk/pc-links.htm>.