'in' operator and feature detection technique...

  • Thread starter Luke Matuszewski
  • Start date
L

Luke Matuszewski

We all know that feature detection technique works from very beggining
of user-agents supporting JavaScript. We can alway check if eg.
document has a write property or smth else:

if(document.write) {

}

We could do that for all of objects, so i have been surprised when i
found 'in' operator, which for above example would be used like this:

if("write" in document) {

}

So i have questioned myself what for ? I can always do:

if(document["write"]) {

}

or even
var prop = [...];

if(document[prop]) {

}

which is supported better then 'in' operator ('in' is supported since
W. IE 5.5 and NN 6 - around 2000 year). I can only guess that 'in' was
provided in W. IE 5.5 only for convenience... but that is my guess and
someone more knowlegable could write here some more opinions on this
operator...

B.R.
Luke Matuszewski
 
L

Luke Matuszewski

Luke Matuszewski napisal(a):
if(document.write) {
if(document["write"]) {
var prop = [...];

if(document[prop]) {

, which will not work if document has a write property and it has null
or undefinded value (so in operator can tell if object has property in
question even if this property is null or undefined).
if("write" in document) {

, results true if document has write property even if it is null or
undefined.

I do not see other reasons for using 'in' operator (detecting property
of object even if it is null or undefined). Here is a test case:

var ob = { prop: " [ property value ] " };
if(ob.prop) {
alert("feature detection: " + ob.prop);
}

if("prop" in ob) {
alert("in operator: " + ob.prop);
}

ob.prop = null;

if(ob.prop) {
alert("feature detection(ob.prop==null): " + ob.prop);
}

if("prop" in ob) {
alert("in operator(ob.prop==null): " + ob.prop);
}

ob.prop = window.window1234567890; /* ob.prop == undefined */

if(ob.prop) {
alert("feature detection(ob.prop==null): " + ob.prop);
}

if("prop" in ob) {
alert("in operator(ob.prop==null): " + ob.prop);
}

B.R.
Luke Matuszewski
 
M

Martin Honnen

Luke Matuszewski wrote:

if("write" in document) {
So i have questioned myself what for ? I can always do:

if(document["write"]) {

I can only guess that 'in' was
provided in W. IE 5.5 only for convenience...

The in operator checks whether there is a property with the name as the
first operand, that is much different to converting the property value
to a boolean (which if () does).

Example

var testObject = {
b : false,
s : '',
n: 0
};

var results = '';

for (var propertyName in testObject) {
results += 'Boolean(obj["' + propertyName + '"]): ' +
Boolean(testObject[propertyName]) + '\r\n';
results += '"' + propertyName + '" in obj: ' +
(propertyName in testObject) + '\r\n\r\n';
}

results


yields

Boolean(obj["b"]): false
"b" in obj: true

Boolean(obj["s"]): false
"s" in obj: true

Boolean(obj["n"]): false
"n" in obj: true
 
T

Thomas 'PointedEars' Lahn

VK said:
('property' in someObject) is not intended for features test - though
it can be used and it is used this way (when the support for
prehistoric browsers is not a requirement).

So your history begins not long before 2000 CE? That would explain some
of your misconceptions, although not all of them.
But originally it was introduced with it counterpair hasOwnProperty for
prototype-based inheritance management.

Nonsense.

JavaScript 1.0 and ECMAScript implementations (e.g. JavaScript 1.1+, JScript
1.0+) have always been languages that used prototype-based inheritance.

The `in' operator was introduced in JavaScript 1.5 (Mozilla/5.0 rv:0.6,
November 2000), JScript 5.5 (IE 5.5, July 1999) [1], and ECMAScript
Edition 3 (December 1999).

The `hasOwnProperty' method was introduced in JavaScript 1.5, JScript 5.5,
and ECMAScript Edition 3.

Since the current major version of IE is 6.0, that would mean you consider
its previous major version, IE 5.0, historic already, even though it is
still used. I take that as another proof that what you post should be
handled with extreme care.
P.S.
The "in" operator checks if an object has a property named property. It
also checks the object's prototype to see if the property is part of
the prototype chain.

The operator simply uses the prototype chain, by calling the internal
GetValue() method (ES3 Final, 8.7.1) which calls the internal [[Get]]
method (8.6.2.1) which calls the [[Get]] method of [[Prototype]] if it
is not `null' (steps 4 and 5), _up to its end_ (including the prototype
of the prototype aso.). It does not check only the object's prototype
explicitly as that would not be sufficient.


PointedEars
___________
[1] The JScript and JScript.NET References say it was introduced in JScript
1.0 already, that would mean IE 3.0 (August 1996). However, I find that
hard to believe and think that is an error, since a) ECMAScript Ed. 3
was not published yet and b) it also says that `for (... in ...)' was
not supported before JScript 5.5 (IE 5.5). I would appreciate it if
someone could provide reliable test results to back up either claim.
 
V

VK

Thomas said:
So your history begins not long before 2000 CE? That would explain some
of your misconceptions, although not all of them.

And what your history begins with? 1995? The oldest IE currently
supported by Microsoft is IE 5.5 SP2. This is the oldest version one
can hold by claming "corporate demands". Any older versions are being
kept by few individuals for reasons which are out of my interest.
If NN4, IE4, Opera 6 etc. users still want to enjoy the modern web w/o
_free_ updates then they are welcome to join into "Old Browsers User
Society" and donate into special fund which would pay to Yahoo, MSN,
myself and any other developers for extra solutions for outdated
browsers. But I'm affraid that they are willing to spend their money
for my extra efforts as much as I willing to spend extra efforts for
them for free.

I'm supporting JavaScript 1.5 and higher, JScript 5.6 plus a bunch of
half-a** done DOM implementations made over the last few years. That's
already 50% volunteer work not covered by my payroll.

And I need to sit on my spare day for free because some John Doe
bothers to spend 10 min to update his Opera 3.0 to Opera 8.51 ? Kiss
my..
JavaScript 1.0 and ECMAScript implementations (e.g. JavaScript 1.1+, JScript
1.0+) have always been languages that used prototype-based inheritance.

What inheritance?!? JavaScript that did not have any inheritance - not
prototype based, not classical. You simply cannot create anything -
only declare variables and add properties to window object. Plus Math
and Date objects.
The `in' operator was introduced in JavaScript 1.5 (Mozilla/5.0 rv:0.6,
November 2000), JScript 5.5 (IE 5.5, July 1999) [1], and ECMAScript
Edition 3 (December 1999).

The `hasOwnProperty' method was introduced in JavaScript 1.5, JScript 5.5,
and ECMAScript Edition 3.

Yes, exactly because developers got all tools for fully functional
inheritance and they needed (or at least it was thought so) traking
tools for inherited members.
Since the current major version of IE is 6.0, that would mean you consider
its previous major version, IE 5.0, historic already, even though it is
still used.

See above
The operator simply uses the prototype chain, by calling the internal
GetValue() method (ES3 Final, 8.7.1) which calls the internal [[Get]]
method (8.6.2.1) which calls the [[Get]] method of [[Prototype]] if it
is not `null' (steps 4 and 5), _up to its end_ (including the prototype
of the prototype aso.). It does not check only the object's prototype
explicitly as that would not be sufficient.

If you call it "simply" then so be it :)
You can forward this explanation to Microsoft, because they seem in the
dark how does their operator work.
 
L

Luke Matuszewski

Thomas 'PointedEars' Lahn napisal(a):
[1] The JScript and JScript.NET References say it was introduced in JScript
1.0 already, that would mean IE 3.0 (August 1996). However, I find that
hard to believe and think that is an error, since a) ECMAScript Ed. 3
was not published yet and b) it also says that `for (... in ...)' was
not supported before JScript 5.5 (IE 5.5). I would appreciate it if
someone could provide reliable test results to back up either claim.
From my past posts i have done some testing in 'in' operator and others
(which revealed some features of JavaScript 1.2 (1.3) / JScript
3.0/IE4):
- for(... in ...) construct is supported since JavaScript 1.2 /
JScript 3.0/IE4, but expressions like [string] in objRef (resulting of
Boolean value) are not supported since IE5.5/JScript 5.5, JavaScript
1.5(?);

others:

- strict equality operators === and !== are supported since JavaScript
1.3 / JScript 3/IE4
- anonymous and named function expressions are supported since
JavaScript 1.3 / JScript 3(?)/IE4 (althought they were not included in
ECMAScript Ed. 1);
- switch/case/default, delete, do/while, labeled continue and labeled
break with array/object initializer ( [ ] / { } ) are supported since
JavaScript 1.2 / JScript 3/IE4 (althought they were not included in
ECMAScript Ed. 1);
- nesting functions inside functions is supported since JavaScript 1.2
/ JScript 3(?)/IE4 (althought they were not included in ECMAScript Ed.
1);

(?) - not 100% sure, maybe someone more knowlegable will correct this;
(since features mentioned above are widely used when creating scripts,
the baseline for those scripts are IE 4 / NN 4(.06)).

B.R.
Luke.
 
L

Luke Matuszewski

Luke Matuszewski napisal(a):
[...] delete [...]
(were in ECMAScript Ed. 1);

As a final note, ECMAScript Ed. 2 is only a rewriting of ECMAScript Ed.
1 to comply to ISO/IEC 16262 standard (so no new features were added
till ECMAScript Ed. 3).

B.R.
Luke Matuszewski
 
V

VK

Luke said:
- for(... in ...) construct is supported since JavaScript 1.2 /
JScript 3.0/IE4, but expressions like [string] in objRef (resulting of
Boolean value) are not supported since IE5.5/JScript 5.5, JavaScript
1.5(?);

There are:

for (...in...) {...} Statement

in Operator // if ('something' in something)

for (...in...) *statement* is supported "since forever". It means that
when the first sketchy descriptions of JavaScript appeared (before any
ECMA and versioning), for (...in...) statement was already there in the
same form as it is now. Possibly it was not presented in the fist
drafts of LiveScript - I did not work with it.

in *operator* has been introduced in JScript 5.0 / JavaScript 1.5

While preparing the documentation for JScript 5.6, a typo had been made
so versions are being switched:
for (...in...) *statement* is marked as supported since JScript 5.0 and
in *operator* as supported since JScript 1.0

Switch the versions and you will get the right picture.

Unfortunately this typo was reproduced in a number of places as I can
tell. You are welcome to report it to all involved organizations under
your name if you want to. Overall this documentation bug wouldn't be
discovered without your post.
 
T

Thomas 'PointedEars' Lahn

VK said:
Luke said:
- for(... in ...) construct is supported since JavaScript 1.2 /
JScript 3.0/IE4, but expressions like [string] in objRef (resulting of
Boolean value) are not supported since IE5.5/JScript 5.5, JavaScript
1.5(?);

There are:

for (...in...) {...} Statement

in Operator // if ('something' in something)

for (...in...) *statement* is supported "since forever". It means that
when the first sketchy descriptions of JavaScript appeared (before any
ECMA and versioning), for (...in...) statement was already there in
the same form as it is now. Possibly it was not presented in the fist
drafts of LiveScript - I did not work with it.

in *operator* has been introduced in JScript 5.0 / JavaScript 1.5
[...]
Switch the versions and you will get the right picture.
[...]

That is not quite correct.

The Guides for JavaScript 1.0 and 1.1, the JavaScript 1.2 Reference, and
the Core JavaScript 1.3 to 1.5 References say the same about the `for (...
in ...)' statement ("Implemented in: JavaScript 1.0, NES 2.0, ECMA[Script]
[Edition]: ECMA-262 [June 1997]").

There is no mention of a standalone `in' operator before Core JavaScript
1.4.

Since we know that Microsoft JScript 1.0 (August 1996) was nothing more
than an enhanced copy of JavaScript 1.0/1.1 (March/August 1996), there is
good reason to believe that the `for (... in ...)' statement was already
supported in that first JScript version indeed. It is also conclusive that
after Netscape introduced the standalone `in' operator in JavaScript 1.4
(1998/1999; implemented server-side only), later specified in ECMAScript
Edition 3 (December 1999), Microsoft implemented it in JScript 5.0 (March
1999; IE 5.0). (I will modify my JS/ECMAScript Support Matrix accordingly.)

That does not make your initial statement in this thread reasonable, though.


PointedEars
 
L

Luke Matuszewski

Thomas 'PointedEars' Lahn napisal(a):
standalone `in' operator [...]
Microsoft implemented it in JScript 5.0

You are wrong. The standalone 'in' operator was implemented in W. IE
5.5+ (it was not implemeneted in JScript 5.1/W.IE5 SP2). Here is a test
case i used:

<script type="text/javascript">
var obj = {};
obj.prop = "sample";
if("prop" in obj) alert("yes"); // alerts "yes" only on W.IE5.5 and
above, in W.IE 5 yelds error
</script>

, on Standalone Windows Internet Explorers from:
<URL:downloads.skyzyx.com/>

W.IE - Windows Internet Explorer (there is also Mac Internet Explorer,
since 5.1 it has ECMAScript Ed. 3 compilance).

B.R.
Luke Matuszewski
 
L

Luke Matuszewski

Furthermore there is a typeof operator which is supported since
JavaScript 1.1 and JScript 2.0, which works almost like 'in' operator
(the only case it 'fails' is when property of object exists and have
undefined value). Here is an example:

var obj = new Object();
obj.prop = "string 1";

if(typeof(obj.prop) != 'undefined') {
alert("obj.prop exists"); //yelds
}

if("prop" in obj) {
alert("obj.prop exists"); //yelds
}

obj.prop = window.window1234567890;

if(typeof(obj.prop) != 'undefined') { //actually obj.prop exists and
has a value undefined...
alert("obj.prop exists"); // NOT yelds
}

if("prop" in obj) {
alert("obj.prop exists"); //yelds
}

Generally typeof is more supported, and i think suggested way to detect
the existence of property.

B.R.
Luke Matuszewski.
 
T

Thomas 'PointedEars' Lahn

Luke said:
Thomas 'PointedEars' Lahn napisal(a):
standalone `in' operator [...]
Microsoft implemented it in JScript 5.0

You are wrong.

You want to learn to quote. NOW.

I have not stated that it is so. I have said that there is reason to
believe that VK is right regarding the version mixup in the MSDN Library
documentation. I cannot be proven to have been wrong with the above
because I have never said it.
The standalone 'in' operator was implemented in W. IE
5.5+ (it was not implemeneted in JScript 5.1/W.IE5 SP2).

Fair enough, that still fits the pattern of JScript implementation after
JavaScript, and makes VK's initial argument that `in' could be used when
"prehistoric browser" support was not required even less reasonable.


PointedEars
 
T

Thomas 'PointedEars' Lahn

Luke said:
Furthermore there is a typeof operator which is supported since
JavaScript 1.1 and JScript 2.0, which works almost like 'in' operator
(the only case it 'fails' is when property of object exists and have
undefined value). [...]

Why the quotes? It definitely fails in this case or when the object
inherits the property through the prototype chain with this particular
value.
Generally typeof is more supported, and i think suggested way to detect
the existence of property.

We had this argument before, remember? `typeof' cannot be used to detect
the existence of a property reliably. However, there is no better way with
host objects, and it is usually sufficient.


PointedEars
 
L

Luke Matuszewski

Luke Matuszewski wrote:
Thomas said:
You want to learn to quote. NOW.

What is wrong with my quotes (please describe if you have some time)
? (ps my intention was not to hurt your pride publicly or something
like that, obviously it seems it is your character is too impetuous).

B.R.
Luke Matuszewski
 
T

Thomas 'PointedEars' Lahn

Luke said:
Luke Matuszewski wrote:


What is wrong with my quotes (please describe if you have some time)
?

First you destroyed the context of my statement, then
you said I was wrong, referring only to what was left.


PointedEars
 
V

VK

Thomas said:
The Guides for JavaScript 1.0 and 1.1, the JavaScript 1.2 Reference, and
the Core JavaScript 1.3 to 1.5 References say the same about the `for (...
in ...)' statement ("Implemented in: JavaScript 1.0, NES 2.0, ECMA[Script]
[Edition]: ECMA-262 [June 1997]").

There is no mention of a standalone `in' operator before Core JavaScript
1.4.

JavaScript 1.4 was a version that "never became". It was a version to
use for client-server transactions but no one transaction was ever done
using it (besides the test runs within the Netscape office). The war
was lost and new masters (AOL) were not interested in internees' side
researches.
Since we know that Microsoft JScript 1.0 (August 1996) was nothing more
than an enhanced copy of JavaScript 1.0/1.1 (March/August 1996), there is
good reason to believe that the `for (... in ...)' statement was already
supported in that first JScript version indeed. It is also conclusive that
after Netscape introduced the standalone `in' operator in JavaScript 1.4
(1998/1999; implemented server-side only), later specified in ECMAScript
Edition 3 (December 1999), Microsoft implemented it in JScript 5.0 (March
1999; IE 5.0). (I will modify my JS/ECMAScript Support Matrix accordingly.)

That does not make your initial statement in this thread reasonable, though.

That places things in the right order: for (... in ... ) statement was
implemented since JS ever was, (...in...) operator is implemented since
JS 5.0 (IE) / 1.5 (NN=>FF)
 
L

Luke Matuszewski

VK napisal(a):
That places things in the right order: for (... in ... ) statement was
implemented since JS ever was, (...in...) operator is implemented since
JS 5.0 (IE) / 1.5 (NN=>FF)

Since JScript 5.5 (IE5.5) / JavaScript 1.5 (NN6, all FF, all Mozila) /
Opera 6 / Safari 1.2. (tests provied in prevous posts, and tested on
Windows Internet Explorer from <URL:downloads.skyzyx.com>).
 
V

VK

Luke said:
Since JScript 5.5 (IE5.5) / JavaScript 1.5 (NN6, all FF, all Mozila) /
Opera 6 / Safari 1.2. (tests provied in prevous posts, and tested on
Windows Internet Explorer from <URL:downloads.skyzyx.com>).

Correct for IE: JScript 5.0 (Internet Explorer 5.0) supports statements

if ('something' in something)
for Windows

It is not clear for Mac platforms
 
L

Luke Matuszewski

VK napisal(a):
Correct for IE: JScript 5.0 (Internet Explorer 5.0) supports statements

if ('something' in something)
for Windows

Then i have buggy Windows Internet Explorer implementations and site
<URL:downloads.skyzyx.com> provided buggy/modified standalone microsoft
internet explorers which in those versions they removed 'in' standalone
operator support from theirs Internet Explorer 5 SP2 (JScript
5.1.0.5010) (my tests provided in this post runed on WIE 3 to WIE 6,
and only WIE5.5 and above passed it without errors). On W. IE 5 there
was an error:

<quote>
Line: 16
Char: 11
Error: Expected character ')'
Code: 0
URL: [file://C:\Devel\Apache2\www\funcexpr.htm]
<quote>

which was (in my test htm file):
if("prop" in obj) {
^
|- is line 16, char 11...

Any comments ?

B.R.
Luke Matuszewski
 
T

Thomas 'PointedEars' Lahn

VK said:
Thomas said:
The Guides for JavaScript 1.0 and 1.1, the JavaScript 1.2 Reference, and
the Core JavaScript 1.3 to 1.5 References say the same about the `for
(... in ...)' statement ("Implemented in: JavaScript 1.0, NES 2.0,
ECMA[Script]
[Edition]: ECMA-262 [June 1997]").

There is no mention of a standalone `in' operator before Core JavaScript
1.4.

JavaScript 1.4 was a version that "never became".
It was a version to use for client-server transactions but no one
transaction was ever done using it (besides the test runs within the
Netscape office). The war was lost and new masters (AOL) were not
interested in internees' side researches.

Utter nonsense. I have already said that JavaScript 1.4 (1998/1999) is
implemented server-side only. The server that supported it was Netscape
Enterprise Server 4.0. What is true only is that AOL/TW acquired Netscape
Comm. on November 24, 1998, which led to the formation of iPlanet Inc.,
a corporation jointly owned by Sun Microsystems, Inc. and AOL, and the
release of NES 4.1 as iPlanet Web Server 4.1. After AOL finally sold the
remaining portion of its interest in iPlanet to Sun, the brand changed
again to Sun ONE Web Server to what is now called Sun Java (Enterprise)
System (JES) Web Server. Sun ONE Server still supported Server-Side
JavaScript 1.4, and since the Java System Web Server incorporates its
features, it is likely that it also supports Server-Side JavaScript 1.4.
There are also other Web servers that support SSJS, most certainly
version 1.4.
[...]
That does not make your initial statement in this thread reasonable,
though.

You overlooked that.
That places things in the right order: for (... in ... ) statement was
implemented since JS ever was, (...in...) operator is implemented since
JS 5.0 (IE) / 1.5 (NN=>FF)

Apparently your statement does not hold water for the standalone `in'
operator. The last part of your sentence is worded confusingly, BTW.


PointedEars
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,577
Members
45,052
Latest member
LucyCarper

Latest Threads

Top