Javascript [Electronic resources] : The Definitive Guide (4th Edition) نسخه متنی

اینجــــا یک کتابخانه دیجیتالی است

با بیش از 100000 منبع الکترونیکی رایگان به زبان فارسی ، عربی و انگلیسی

Javascript [Electronic resources] : The Definitive Guide (4th Edition) - نسخه متنی

David Flanagan

| نمايش فراداده ، افزودن یک نقد و بررسی
افزودن به کتابخانه شخصی
ارسال به دوستان
جستجو در متن کتاب
بیشتر
تنظیمات قلم

فونت

اندازه قلم

+ - پیش فرض

حالت نمایش

روز نیمروز شب
جستجو در لغت نامه
بیشتر
لیست موضوعات
توضیحات
افزودن یادداشت جدید


8.7 Object Properties and Methods


As we discussed earlier, all objects in JavaScript inherit from the

Object class. While
more specialized classes, such as the built-in String class or a
user-defined Complex class, define properties and methods of their
own, all objects, whatever their class, also support the properties
and methods defined by the Object class. Because of their
universality, these properties and methods are of particular
interest.


8.7.1 The constructor Property




Starting with
JavaScript 1.1, every object has a constructor
property that refers to the constructor function used to initialize
the object. For example, if I create an object o
with the Complex( ) constructor, the property
o.constructor refers to
Complex:

var o = new Complex(1,2);
o.constructor == Complex; // Evaluates to true

Each Complex object (or object of whatever type) does not have its
own unique constructor property, of course;
instead, this property is inherited from the prototype object. As
discussed earlier in this chapter, JavaScript creates a
prototype
object for each constructor function you define
and assigns that object to the
prototype property of the constructor. What I did
not reveal earlier, however, is that the prototype object is not
initially empty. When created, it includes a
constructor property that refers to the
constructor function. That is, for any function f,
f.prototype.constructor is always equal to
f (unless we set it to something else).

Since the constructor function defines the class of an object, the
constructor property can be a powerful tool for
determining the type of any given object. For example, you might use
code like the following to determine the type of an unknown object:

if ((typeof o == "object") && (o.constructor == Date))
// Then do something with the Date object...

The existence of the constructor property is not
always guaranteed, however. The author of a class might replace the
prototype object of a constructor with an entirely new object, for
example, and the new object might not have a valid
constructor property.


8.7.2 The toString( ) Method



The toString( )
method takes
no
arguments; it returns a string that somehow represents the type
and/or value of the object on which it is invoked. JavaScript invokes
this method of an object whenever it needs to convert the object to a
string. This occurs, for example, when you
use the + operator to concatenate a string with an
object or when you pass an object to a method such as alert(
) or document.write( ).

The default toString( ) method is not very
informative. For example, the following lines of code simply cause
the browser to display the string "[object
Object]":[6]

[6] In client-side JavaScript in
Netscape, if the language attribute of the
<script> tag is explicitly set to
"JavaScript1.2", the toString( )
method behaves differently: it displays the names and values of all
the fields of the object, using object literal notation. This
violates the ECMAScript specification.

c = new Circle(1, 0, 0);
document.write(c);

Because this default method does not display much useful information,
many classes define their own versions of toString(
). For example, when an array is converted to a string, we
obtain a list of the array elements, themselves each converted to a
string, and when a function is converted to a string, we obtain the
source code for the function.

The idea behind toString( ) is that
each class of objects has its own
particular string representation, so it should define an appropriate
toString( ) method to convert objects to that
string form. Thus, when you define a class, you should define a
custom toString( ) method for it so that instances
of the class can be converted to meaningful strings. The string
should contain information about the object being converted, as this
is useful for debugging purposes. If the string conversion is chosen
carefully, it can also be useful in programs themselves.

The following code shows a toString( ) method we
might define for the Circle class of Example 8-5:

Circle.prototype.toString = function (  ) {
return "[Circle of radius " + this.r + ", centered at ("
+ this.x + ", " + this.y + ").]";
}

With this toString( ) method defined, a typical
Circle object might be converted to the string "[Circle of
radius 1, centered at (0,0).]".

If you look back at Example 8-6, you'll see
that it defines a toString( ) method for our
Complex class of complex numbers.

One interesting feature of the default toString( )
method defined by the Object class is that it reveals some internal
type information about built-in objects. This default
toString( ) method always returns a string of the
form:

[object class]

class
is the internal type of the object and usually corresponds to the
name of the constructor function for the object. For example, Array
objects have a class of
"Array", Function objects have a
class of "Function", and Date
objects have a class of
"Date". The built-in Math object has a
class of "Math", and all Error
objects (including instances of the various Error subclasses) have a
class of "Error". Client-side
JavaScript objects and any other objects defined by the JavaScript
implementation have an implementation-defined
class (such as "Window",
"Document", or "Form").
User-defined objects, such as the
Circle and Complex classes defined earlier in this chapter, always
have a class of "Object".

Note that this class value provides useful
information that is not supplied by the typeof
operator (which returns either "Object" or
"Function" for all objects). The
class value provides information like that
provided by the constructor property described
earlier, but the class value provides it
in the form of a string, instead of in the form of a constructor
function. The only way to obtain this
class value, however, is through the
default toString( ) method defined by Object. Because
classes often define their own versions of this method, we cannot
simply invoke the toString( ) method of an object:

o.toString()  // May invoke a customized toString(  ) method for the object 

Instead, we have to refer explicitly to the default
toString( ) function as the
Object.prototype.toString object and use the
apply( ) method of the function to invoke it on
the desired object:

Object.prototype.toString.apply(o);  // Always invokes the default toString(  ) 

We can use this technique to define a
function that provides
enhanced "type of" functionality:

// An enhanced "type of" function. Returns a string that describes the
// type of x. Note that it returns "Object" for any user-defined object types.
function Typeof(x) {
// Start with the typeof operator
var t = typeof x;
// If the result is not vague, return it
if (t != "object") return t;
// Otherwise, x is an object. Get its class value to try to
// find out what kind of object it is.
var c = Object.prototype.toString.apply(x); // Returns "[object class]"
c = c.substring(8, c.length-1); // Strip off "[object" and "]"
return c;
}


8.7.3 The toLocaleString( ) Method


In ECMAScript v3

and
JavaScript 1.5, the Object class defines a
toLocaleString( ) method in addition to its
toString( ) method. The purpose of this method is
to return a localized string representation of the object. The
default toLocaleString( ) method defined by Object
doesn't do any localization itself; it always return exactly
the same thing as toString( ). Subclasses,
however, may define their own versions of toLocaleString(
). In ECMAScript v3, the

Array, Date, and Number classes do define
toLocaleString( ) methods that return localized
values.


8.7.4 The valueOf( ) Method


The valueOf( )
method is much like the
toString( ) method, but it is called when
JavaScript needs to convert an object to some
primitive type other than a
string -- typically, a number. Where possible, the function should
return a primitive value that somehow represents the value of the
object referred to by the this keyword.

By definition, objects are not primitive values, so most objects do
not have a primitive equivalent. Thus, the default valueOf(
) method defined by the Object class performs no conversion
and simply returns the object on which it is invoked. Classes such as
Number and Boolean have obvious primitive equivalents, so they
override the valueOf( ) method to return
appropriate primitive values. This is why Number and Boolean objects
can behave so much like their equivalent primitive values.

Occasionally, you may define a class that has some reasonable
primitive equivalent. In this case, you may want to define a custom
valueOf( ) method for the class. If you refer back
to Example 8-6, you'll see that we defined a
valueOf( ) method for the
Complex class. This method
simply returned the real part of the complex number. Thus, when a
Complex object is used in a numeric context, it behaves as if it were
a real number without its imaginary component. For example, consider
the following code:

var a = new Complex(5,4);
var b = new Complex(2,1);
var c = Complex.subtract(a,b); // c is the complex number {3,3}
var d = a - b; // d is the number 3

One note of caution about defining a valueOf( )
method: the valueOf( ) method can, in some
circumstances, take priority over the toString( )
method when converting an object to a string. Thus, when you define a
valueOf( ) method for a class, you may need to be
more explicit about calling the toString( ) method
when you want to force an object of that class to be converted to a
string. To continue with the Complex example:

alert("c = " + c);             // Uses valueOf(  ); displays "c = 3"
alert("c = " + c.toString( )); // Displays "c = {3,3}"


8.7.5 The hasOwnProperty( ) Method


The hasOwnProperty(
) method returns true
if the object locally defines a noninherited property with the name
specified by the single string argument. Otherwise, it returns
false. For example:

var o = new Object(  );
o.hasOwnProperty("undef"); // false: the property is not defined
o.hasOwnProperty("toString"); // false: toString is an inherited property
Math.hasOwnProperty("cos"); // true: the Math object has a cos property


8.7.6 The propertyIsEnumerable( ) Method


The propertyIsEnumerable(
) method returns
true if the object defines a property with the
name specified by the single string argument to the method and if
that property would be enumerated by a for/in
loop. Otherwise, it returns false. For example:

var o = { x:1 };
o.propertyIsEnumerable("x"); // true: property exists and is enumerable
o.propertyIsEnumerable("y"); // false: property doesn't exist
o.propertyIsEnumerable("valueOf"); // false: property isn't enumerable

Note that the ECMAScript specification states that
propertyIsEnumerable( ) considers only properties
defined directly by the object, not inherited properties. This
unfortunate restriction makes the function less useful, because a
return value of false may mean either that the
property is not enumerable or that it is enumerable but is an
inherited property.


8.7.7 The isPrototypeOf( ) Method


The isPrototypeOf(
) method returns true
if the object is the prototype object of the argument. Otherwise, it
returns false. Using this method is similar to
using the constructor property of an object. For
example:

var o = new Object(  );
Object.prototype.isPrototypeOf(o); // true: o.constructor == Object
Object.isPrototypeOf(o); // false
o.isPrototypeOf(Object.prototype); // false
Function.prototype.isPrototypeOf(Object); // true: Object.constructor == Function


/ 844