rh said:
Given that propertyIsEnumerable doesn't venture into the prototype
chain, a hasOwnProperty check would seem to redundant. So my later
suggestion would be to simply replace the hasOwnProperty with a
propertyIsEnumerable check;
I put together a test page. Had a curious result when attempting to set
the __proto__ property of an array and object... Variable not set and
not error message. Strange deal indeed... if I got it right.
Robert
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"
http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<title>Associative tests</title>
<script type="text/javascript">
function smallString(myInput)
{
if (typeof myInput == "undefined" )
{ return myInput; }
else
{
var alpha = myInput.toString();
alpha = alpha.split("{")[0];
return alpha;
}
}
function checkArray(myInput)
{
var myDel = typeof myInput == "string"? "'" : " ";
document.write( "<tr>" +
"<td>myArray[" + myDel + myInput + myDel + "]</td>" +
"<td>" + smallString(myArray[myInput]) + "</td>" +
"<td>" +
(myArray.hasOwnProperty?myArray.hasOwnProperty(myInput):" ")+
"</td>" +
"<td>" +
(myArray.propertyIsEnumerable?myArray.propertyIsEnumerable(myInput):"&nbs
p;")+
"</td>" +
"<td>" +
(myArray.isPrototypeOf?Array.prototype.propertyIsEnumerable(myInput):"&nb
sp;")+
"</td>" +
"<tr>");
}
function checkObject(myInput)
{
var myDel = typeof myInput == "string"? "'" : " ";
document.write( "<tr>" +
"<td>myObject[" + myDel + myInput + myDel + "]</td>" +
"<td>" + smallString(myObject[myInput]) + "</td>" +
"<td>" +
(myObject.hasOwnProperty?myObject.hasOwnProperty(myInput):" ")+
"</td>" +
"<td>" +
(myObject.propertyIsEnumerable?myObject.propertyIsEnumerable(myInput):"&n
bsp;")+
"</td>" +
"<td>" +
(myObject.isPrototypeOf?Object.prototype.propertyIsEnumerable(myInput):"&
nbsp;")+
"</td>" +
"<tr>");
}
</script>
</head>
<body>
<p>See the results of hasOwnProperty, and propertyIsEnumerable
for an <b>Array</b>.
</p>
<table>
<thead>
<th>
variable
</th>
<th>
value<br>trimmed
</th>
<th>
myArray.<br>has<br>Own<br>Property
</th>
<th>myArray.<br>property<br>Is<br>Enumerable
</th>
<th>
Array.<br>prototype.<br>property<br>Is<br>Enumerable
</th>
</thead>
<tbody>
<script type="text/javascript">
var myArray = ['zero'];
myArray[2] = 'thing';
Array.prototype.pi = 3.14159;
myArray['myIndex'] = 'something';
checkArray(2);
checkArray('2');
checkArray('myIndex');
checkArray('pop');
checkArray('toString');
checkArray('pi');
checkArray('noIndex');
checkArray('hasOwnProperty');
checkArray('__proto__');
</script>
</table>
<br>
<p>
Using join() the data in the array is:
<script type="text/javascript">
document.write(myArray.join());
document.write(" and has " + myArray.length + " elements with numeric
indexes.");
</script>
</p><p>Using in the list in indexes for myArray is:
<script type="text/javascript">
var accum;
var begun = false;
for (var i in myArray)
{
if ( begun == true )
{ accum += ", " + i }
else
{ accum = i;
begun = true; }
}
document.write(accum);
</script>
</p>
<br>
<p>See the results of hasOwnProperty, and propertyIsEnumerable
for an <b>Object</b>.
</p>
<table>
<thead>
<th>
variable
</th>
<th>
value<br>trimmed
</th>
<th>
myArray.<br>has<br>Own<br>Property
</th>
<th>myArray.<br>property<br>Is<br>Enumerable
</th>
<th>
Array.<br>prototype.<br>property<br>Is<br>Enumerable
</th>
</thead>
<script type="text/javascript">
var myObject = {'declared': 'data'};
myObject[2] = 'thing';
Object.prototype.pi = 3.14159;
myObject['myIndex'] = 'something';
checkObject(2);
checkObject('2');
checkObject('myIndex');
checkObject('declared');
checkObject('pop');
checkObject('toString');
checkObject('toLocaleString');
checkObject('pi');
checkObject('noIndex');
checkObject('hasOwnProperty');
checkObject('__proto__');
</script>
</table>
<br>
<p>Using in the list in indexes for myObject is:
<script type="text/javascript">
var accum;
var begun = false;
for (var i in myObject)
{
if ( begun == true )
{ accum += ", " + i }
else
{ accum = i;
begun = true; }
}
document.write(accum);
</script>
</p>
<p>Assign new values to <b>myArray</b>.
<table>
<thead>
<th>
variable
</th>
<th>
value<br>trimmed
</th>
<th>
myArray.<br>has<br>Own<br>Property
</th>
<th>myArray.<br>property<br>Is<br>Enumerable
</th>
<th>
Array.<br>prototype.<br>property<br>Is<br>Enumerable
</th>
</thead>
<tbody>
<script type="text/javascript">
myArray['pop'] = 'something';
myArray['__proto__'] = "my thing";
checkArray('pop');
checkArray('__proto__');
</script>
</table>
<p>
Using join() the data in the array is:
<script type="text/javascript">
document.write(myArray.join());
document.write(" and has " + myArray.length + " elements with numeric
indexes.");
</script>
</p><p>Using in the list in indexes for myArray is:
<script type="text/javascript">
var accum;
var begun = false;
for (var i in myArray)
{
if ( begun == true )
{ accum += ", " + i }
else
{ accum = i;
begun = true; }
}
document.write(accum);
</script>
</p>
<br>
<br>
<p>Assign some more values to <b>myObject</b>.
</p>
<table>
<thead>
<th>
variable
</th>
<th>
value<br>trimmed
</th>
<th>
myArray.<br>has<br>Own<br>Property
</th>
<th>myArray.<br>property<br>Is<br>Enumerable
</th>
<th>
Array.<br>prototype.<br>property<br>Is<br>Enumerable
</th>
</thead>
<script type="text/javascript">
myObject['toLocaleString'] = 'something';
myObject['__proto__'] = 'my something';
checkObject('toLocaleString');
checkObject('__proto__');
</script>
</table>
<br>
<p>Using in the list in indexes for myObject is:
<script type="text/javascript">
var accum;
var begun = false;
for (var i in myObject)
{
if ( begun == true )
{ accum += ", " + i }
else
{ accum = i;
begun = true; }
}
document.write(accum);
</script>
</p>
<br>
<p>
<script type="application/x-javascript">
document.write(navigator.userAgent);
</script>
</body>
</html>