By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
446,190 Members | 784 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 446,190 IT Pros & Developers. It's quick & easy.

Check if key is defined in associative array

P: n/a
JGH
How can I check if a key is defined in an associative array?

var users = new array();
users["joe"] = "Joe Blow";
users["john"] = "John Doe";
users["jane"] = "Jane Doe";

function isUser (userID)
{
if (?????)
{ alert ("This is a valid ID"); }
else
}

But what goes in place of the ????

Jul 23 '05 #1
Share this Question
Share on Google+
26 Replies


P: n/a
On Wed, 17 Nov 2004 20:21:24 +0000 (UTC), JGH <jo******@nospam.tds.net>
wrote:
How can I check if a key is defined in an associative array?
Just to dispel any misconceptions, there's no such thing as an associative
array in ECMAScript/Javascript. What you are actually using is a feature
of objects - their ability to have properties added at run-time.
var users = new array();
users["joe"] = "Joe Blow";
users["john"] = "John Doe";
users["jane"] = "Jane Doe";
Using an actual array is a waste. You aren't using it to store values by
ordinal number, you're just using the fact that it's an object.

var users = new Object();

or

var users = {}; // Braces, not parentheses

If the list is static, you could write:

var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};

If an id contains an illegal character, specify the property name as a
string:

'mike-winter' : 'Michael Winter'
function isUser (userID)
{
if (?????)
{ alert ("This is a valid ID"); }
else
}

But what goes in place of the ????


If there is no property that goes by the name contained in userID,
attempting to access that property will yield undefined. You can check for
that by comparing the type:

if('undefined' != typeof user[userId]) {
// valid ID
}

Hope that helps,
Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #2

P: n/a
Michael Winter wrote:
On Wed, 17 Nov 2004 20:21:24 +0000 (UTC), JGH <jo******@nospam.tds.net>
wrote:
function isUser (userID)
{
if (?????)
{ alert ("This is a valid ID"); }
else
}

But what goes in place of the ????

If there is no property that goes by the name contained in userID,
attempting to access that property will yield undefined. You can check
for that by comparing the type:

if('undefined' != typeof user[userId]) {
// valid ID
}


Until the day you notice that isUser( "pop" ) alerts that "pop" is a
valid ID, you'll get on fine with this solution.

Why so ? Because pop, (or push, length, slice...) is a member of Array
objects, and you can accidentally fall on it (and its typeof string is
"function"). The two syntaxes, user.pop and user["pop"], have similar
effects.

I advise you to check type against the expected type of user[userId]:

if( 'string' == typeof user[userId] ) {
// valid ID
}

Using arrays as associative containers has pitfalls; you may wish to
read the misnamed thread "Arrays as hash tables"

http://groups.google.com/groups?thre...gle.com&rnum=1

Alexis
Jul 23 '05 #3

P: n/a
On Thu, 18 Nov 2004 10:09:15 +0100, Alexis Nikichine
<al**************@somedomain.fr> wrote:

[snip]
I advise you to check type against the expected type of user[userId]:

if( 'string' == typeof user[userId] ) {
// valid ID
}
Yes, that is better. I forgot about the existing properties that an object
will have, such as toString and prototype.
Using arrays as associative containers has pitfalls [...]


Indeed. Notice that the first thing that both Lasse and Douglas said was
don't use an array. Use a simple object instead.

[snip]

Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #4

P: n/a
JGH
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in
If an id contains an illegal character, specify the property name as a
string [...] Hope that helps,


It helped a lot. I got my old code (the stuff you corrected) off a
tutorial on the web. So that's why I was unaware I was doing it wrong.

Anyway, it mostly works now. Problem is the values for user ids and
names come from a database and may contain illegal values. I'm
generating the list of user ids and names via a few lines of visual
basic. But what it ends up with is something like this:
var users = {
~!# : 'Don't use this id',
'ton : 'O'Neal, Ted',
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};

There are non-alpha characters in the ID and apostrophe's in the name.
That's why I was using quotes in my original code. Is that wrong?


Jul 23 '05 #5

P: n/a
On Thu, 18 Nov 2004 14:55:23 +0000 (UTC), JGH <jo******@nospam.tds.net>
wrote:

[snip]
There are non-alpha characters in the ID and apostrophe's in the name.
That's why I was using quotes in my original code. Is that wrong?


Either single- or double-quotes are fine. I used single out of habit
rather than neccessity. Just make your VB code place double quotes around
all values so you end up with:

var users = {
"~!#" : "Don't use this id",
"'ton : "O'Neal, Ted",
"joe" : "Jow Blow",
"john" : "John Doe",
"jane" : "Jane Doe"
};

I assume that double quotes can't occur but if, for some reason, you do
need to include a double quote, output it as \":

"\"This value contains quotes\""

Good luck,
Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #6

P: n/a
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in message news:<opshmn6wlzx13kvk@atlantis
Using an actual array is a waste. You aren't using it to store values by
ordinal number, you're just using the fact that it's an object.
You can loop through the properties of an object the same way you can
loop through an array?
var users = {}; // Braces, not parentheses
That's interesting. What exactly is being said here? Two braces
suggests, to me, a block of scope or a function. But a function would
usually have a name. Is this sort of like creating a fuction called
users and then, at the same time, creating a reference to it?

If the list is static, you could write:

var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};


This looks to be like an array. If it is not, then what is it?
Jul 23 '05 #7

P: n/a
lk******@geocities.com (lawrence) wrote:
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in message news:<opshmn6wlzx13kvk@atlantis
Using an actual array is a waste. You aren't using it to store values by
ordinal number, you're just using the fact that it's an object.
You can loop through the properties of an object the same way you can
loop through an array?


No, the opposite. You can loop through items in an array the same as
properties of an object.

If you have an array
var a = ["Joe", "John", "Jane"]
you can loop through with the numeric array index
for (var i = 0; i < a.length; i++)
{
echo(a[i]
}
or the property name
for (var i in a)
{
echo(a[i]
}

Using the numeric index is faster because looping through each
property requires allocating memory and initializing strings (the
property names are strings).

However, if you have a very sparse array -- for example, an array with
a length of 1000 but only 5 items in it -- looping by property name is
faster because it iterates over only the 5 actual items whereas
looping numerically iterates over all 1000.
var users = {}; // Braces, not parentheses


That's interesting. What exactly is being said here?


It's an object with no properties (aside from the properties all
Objects have).
Two braces
suggests, to me, a block of scope or a function. But a function would
usually have a name. Is this sort of like creating a fuction called
users and then, at the same time, creating a reference to it?
If the list is static, you could write:

var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};


This looks to be like an array. If it is not, then what is it?


It's an object. It's the short form of
var users = new Object();
users.joe = "Jow Blow";
users.john = "John Doe";
users["jane"] = "Jane Doe";

http://msdn.microsoft.com/library/en...conobjects.asp

Regards,
Steve
Jul 23 '05 #8

P: n/a
On 18 Nov 2004 13:16:07 -0800, lawrence <lk******@geocities.com> wrote:

Steve answered most of your questions, so I'll cover the one thing I
notice he didn't address in detail.
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in message
news:<opshmn6wlzx13kvk@atlantis


[snip]
var users = {}; // Braces, not parentheses


That's interesting. What exactly is being said here? Two braces
suggests, to me, a block of scope or a function. But a function would
usually have a name. Is this sort of like creating a fuction called
users and then, at the same time, creating a reference to it?


As Steve said, it creates an object. To be more specific, it's an object
literal, similar to the other literal types (number, array, regular
expression, and string) in that it assigns an initialised value to an
identifier. In this case, though, the initialisation is just a simple
object like an empty string or array.
If the list is static, you could write:

var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};


This looks to be like an array. If it is not, then what is it?


This is an object literal that contains a list of property names and
values. The property name can be simple like an identifier; essentially
letters, numbers, underscores (_), and Dollar symbols ($).

The property name can also be a number or string literal. In the latter
case, this allows for more complex names that can't be normally be
specified. Note that although a number can be used to name a property, it
doesn't make the object an array. For example:

// Object literal
var obj = {
5 : 'five'
};
obj[5] // 'five'
obj.length // undefined

// Array literal [1]
var obj = [
,,,,, 'five'
];
obj[5] // 'five'
obj.length // 6

Hope that helps,
Mike
[1] Just to explain the series of commas (elisions), they define "empty"
elements. Each elision adds one to the length property of the array, but
it doesn't actually add an array element.

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #9

P: n/a
JGH
Steve van Dongen <st*****@hotmail.com> wrote in
var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};


This looks to be like an array. If it is not, then what is it?


It's an object. It's the short form of
var users = new Object();
users.joe = "Jow Blow";
users.john = "John Doe";
users["jane"] = "Jane Doe";

Probably what happens when you create what looks like a hash array in
javascript is that the interpreter passes that to the code to create an
object which in turn creates a hash array. Proof of at least the first
half of that is in the fact that a hash array has the standard
properties of an object.

So you can't actually create a hash array in javascript -- the
interpreter just won't let you. However, every object you create is
probably actually a hash array.

Hence the reason for much of the confusion, IMO. People see something
like this:

var users = {};

All that says is create an "object" which is a pointer to an array of
pointers to strings, integers, functions, other objects, etc.

It never occured to me before but that's one thing that's nice about
perl. That extra layer of abstraction isn't there. Objects are openly
hashrefs.
Jul 23 '05 #10

P: n/a
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in message
If the list is static, you could write:

var users = {
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};


This looks to be like an array. If it is not, then what is it?


This is an object literal that contains a list of property names and
values. The property name can be simple like an identifier; essentially
letters, numbers, underscores (_), and Dollar symbols ($).

The property name can also be a number or string literal. In the latter
case, this allows for more complex names that can't be normally be
specified. Note that although a number can be used to name a property, it
doesn't make the object an array. For example:

// Object literal
var obj = {
5 : 'five'
};
obj[5] // 'five'
obj.length // undefined

// Array literal [1]
var obj = [
,,,,, 'five'
];
obj[5] // 'five'
obj.length // 6


So object doesn't have a length() method. And when you go obj[5] with
an object, its not an index between the brackets, its a property name?
So you can iterate through the properties of an object much as you
would through a hash table?

What are the differences, in Javascript, between an object and a hash
table that has pointers to properties and functions?
Jul 23 '05 #11

P: n/a
On 20 Nov 2004 22:19:05 -0800, lawrence <lk******@geocities.com> wrote:

The footnotes in this post go into more detail. I'd only read them if
you're comfortable with what you know about the subject. You might get
confused otherwise.

[snip]
So object doesn't have a length() method.
You mean length property. :P

Correct, an object doesn't have its own built-in length property.
And when you go obj[5] with an object, its not an index between the
brackets, its a property name?
Exactly.

Between the brackets you place an expression. It can be simple, like a
number or string, or something more complex like a function call or string
concatenation. This is how you can create property names at run-time.

The expression is evaluated and converted to a string[1], and the property
name is accessed.

The difference between arrays and other objects when assigning to a
property, is that it treats numbers as a special case[2]. Numeric indices
can update the length property of an array, but other names do not.
So you can iterate through the properties of an object much as you would
through a hash table?
For the most part, yes, with a for..in statement:

for(var propName in obj) {
/* propName is a string containing the property name.
* You can access the property value with obj[propName]
*/
}

The important part to note is that properties have attributes. You can't
actually modify these attributes, but they do exist.

There are four: ReadOnly, DontEnum, DontDelete, and Internal. The ability
to enumerate object properties with the code above is affected by the
second attribute, DontEnum. If it's present, you can access the property
directly, but the code above will skip it. Many built-in properties have
this attribute set. Properties you have *created* yourself will never have
this attribute set, so they can always be enumerated.
What are the differences, in Javascript, between an object and a hash
table that has pointers to properties and functions?


Depends on what particular implementation you're contemplating.

The biggest difference is that ECMAScript objects always contain certain
properties such as toString. You have to be careful not to confuse these
existing properties with actual keys.

If you're comparing to Java's Hashtable object, another big difference is
that it can use any object type (as long as it implements the hashCode and
equals methods) as a key, whereas property names are always strings in
ECMAScript.

Hope that helps,
Mike
[1] That part is important. Some hash tables allow you to use different
types as keys, which might lead you to believe that:

var obj = new Object();
var arr = new Array();

arr[obj] = ...;

allows you to assign values based on the actual object (I did once).
However, what happens is the object is converted to a string. As most
objects will simply return '[object Object]', or something similar, you
have to be careful here.

Also note that

arr[5] and arr['5']

are the same as the number will be converted to a string.
[2] It performs, what is effectively,

/* Convert name to string.
*
* e.g. arr[10], arr[0xa] and arr['10']
* all become '10'
*/

propertyName = String(propertyName);

/* If name, converted to a number then back to string,
* remains the same, treat as array index. If not, treat
* as property name.
*
* e.g. 1 arr[10], arr[0xa] and arr['10']
* all become '10'. Converted to a number and back
* to a string is still '10', and as '10' == '10',
* they are all treated as array indices.
* e.g. 2 arr['0xa'] to a number and back to a string
* is '10', but '0xa' != '10' so is a property, not
* not an index.
*/

if(String(Number(propertyName)) == propertyName) {

/* If the array index is greater than, or equal to, the
* length of the array, update the length property.
*/

if(Number(propertyName) >= array.length) {
array.length = Number(propertyName) + 1;
}
}

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #12

P: n/a
JGH wrote:
"Michael Winter" <M.******@blueyonder.co.invalid> wrote in
If an id contains an illegal character, specify the property name as a
string

[...]
Hope that helps,


Anyway, it mostly works now. Problem is the values for user ids and
names come from a database and may contain illegal values. I'm
generating the list of user ids and names via a few lines of visual
basic. But what it ends up with is something like this:

var users = {
~!# : 'Don't use this id',
'ton : 'O'Neal, Ted',
joe : 'Jow Blow',
john : 'John Doe',
jane : 'Jane Doe'
};

There are non-alpha characters in the ID and apostrophe's in the name.
That's why I was using quotes in my original code. Is that wrong?


No, if you can't be guaranteed that the property is going to contain special
characters or not, it would be wise to always surround it in quotation
marks:

var users = {
'~!#' : 'Don\'t use this id',
'\'ton' : 'O\'Neal, Ted',
'joe' : 'Jow Blow',
'john' : 'John Doe',
'jane' : 'Jane Doe'
};

In addition to escaping single quotation marks, you should consider that the
data from the database may contain new line characters and replace those
with \n or \r.

--
Grant Wagner <gw*****@agricoreunited.com>
comp.lang.javascript FAQ - http://jibbering.com/faq

Jul 23 '05 #13

P: n/a
This page says Javascript has associative arrays:

http://www.pageresource.com/jscript/jarray2.htm

A search on Google reveals dozens of such tutorials. Are they all wrong?

Jul 23 '05 #14

P: n/a
On 8 Dec 2004 15:48:10 -0800, <lk******@geocities.com> wrote:
This page says Javascript has associative arrays:

http://www.pageresource.com/jscript/jarray2.htm

A search on Google reveals dozens of such tutorials. Are they all wrong?


They're certainly misleading. For a start, it has nothing to do with
arrays, as I've previously described. Moreover, they are demonstrating a
feature of the language but describing it as something completely
different.

Javascript does not have associative arrays. It just possesses syntax that
can be used in that way. However, a proper hash table requires much more
work.

Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #15

P: n/a
>>>>>>>>.
They're certainly misleading. For a start, it has nothing to do with
arrays, as I've previously described. Moreover, they are demonstrating
a
feature of the language but describing it as something completely
different.
>>>>

Javascript has too many friends, and they are not very good as friends.From what little I've learned in the last 2 months, it seems to me no

other language is so frequently misrepresented by people who know it
well.

I'm thinking of buying a book on Javascript to further my education.
It's a toss up between Danny Goodman's Javascript Bible and the
O'Rielly book. I've heard good things about the O'Rielly book, but I'm
partial to the Goodman book because back in 1995 when I learned
Hypertalk his book on HyperCard was absolutely a blast to read. Any
Javascript books you personally like?

Jul 23 '05 #16

P: n/a
<lk******@geocities.com> skrev i meddelandet
news:11**********************@c13g2000cwb.googlegr oups.com...
<snip>
Any Javascript books you personally like?


Danny Goodman's "Dynamic HTML" is great. Covers CSS, DOM, Javascript and
more. Not a tutorial really, more of a comprehensive reference books with a
lot of examples thrown in.

Joakim Braun
Jul 23 '05 #17

P: n/a
On 8 Dec 2004 20:10:31 -0800, <lk******@geocities.com> wrote:

[snip]
From what little I've learned in the last 2 months, it seems to me no
other language is so frequently misrepresented by people who know it
well.
The thing is: most people don't know it that well at all. I didn't until I
began reading this group.

[snip]
Any Javascript books you personally like?


I've never read any. The only pieces of literature I've read are the
Netscape guides and references, the ECMA-262 Standard, various articles
posted here, and those on Richard Cornford's
(<URL:http://www.litotes.demon.co.uk/>) and Douglas Crockford's
(<URL:http://www.crockford.com/>) site.

Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #18

P: n/a
JRS: In article <11**********************@f14g2000cwb.googlegroups .com>
, dated Wed, 8 Dec 2004 15:48:10, seen in news:comp.lang.javascript,
lk******@geocities.com posted :
This page says Javascript has associative arrays:

http://www.pageresource.com/jscript/jarray2.htm

A search on Google reveals dozens of such tutorials. Are they all wrong?


Please set your system to give proper attributions, such as precede the
quoted material above; or convert to a system that honours accepted
Usenet practice. See sig below. Likewise, please quote some, but not
all, of the previous article; see this newsgroup's Wednesday FAQ.
One cannot reasonably expect consistent or accurate terminology from
arbitrary Web pages. As a general rule, the more pretentious a URL or
site title is, the less reliable the contents are.
And, in response to a different point, a Web browser should be used to
browse the Web, and to fill in simple forms. It should not be used as
an authoring tool, for which use a plain-text editor, word processor, E-
mailer, news-reader, etc.; i.e. well-written, purpose-designed tools.

If you are obliged to enter much text in an unreliable Web-based
service, prepare it independently and copy'n'paste it in.

--
John Stockton, Surrey, UK. ?@merlyn.demon.co.uk Turnpike v4.00 MIME
Web <URL:http://www.uwasa.fi/~ts/http/tsfaq.html> -> Timo Salmi: Usenet Q&A.
Web <URL:http://www.merlyn.demon.co.uk/news-use.htm> : about usage of News.
No Encoding. Quotes before replies. Snip well. Write clearly. Don't Mail News.
Jul 23 '05 #19

P: n/a
Thanks for the tip, Cornford and Crockford's sites are both a bit
amazing. I find myself drowning in technical details, perhaps you could
offer some clarity on them. Reading the article below, (linked to from
Cornford's site) I'm curious if there is ever a time when a Javascript
programmer needs to know anything about the Activation object? Has
there ever been a time when you yourself have needed to use your
knowledge of it in any way? Can I ignore this bit?
=============================

http://www.jibbering.com/faq/faq_notes/closures.html

When an execution context is created a number of things happen in a
defined order. First, in the execution context of a function, an
"Activation" object is created. The activation object is another
specification mechanism. It can be considered as an object because it
ends up having accessible named properties, but it in not a normal
object as it has no prototype (at least not a defined prototype) and it
cannot be directly referenced by javascript code.

The next step in the creation of the execution context for a function
call is the creation of an arguments object, which is an array-like
object with integer indexed members corresponding with the arguments
passed to the function call, in order. It also has length and callee
properties (which are not relevant to this discussion, see the spec for
details). A property of the Activation object is created with the name
"arguments" and a reference to the arguments object is assigned to that
property.

Next the execution context is assigned a scope. A scope consists of a
list (or chain) of objects. Each function object has an internal
[[scope]] property (which we will go into more detail about shortly)
that also consists of a list (or chain) of objects. The scope that is
assigned to the execution context of a function call consists of the
list referred to by the [[scope]] property of the corresponding
function object with the Activation object added at the front of the
chain (or the top of the list).

Then the process of "variable instantiation" takes place using an
object that ECMA 262 refers to as the "Variable" object. However, the
Activation object is used as the Variable object (note this, it is
important: they are the same object). Named properties of the Variable
object are created for each of the function's formal parameters, and if
arguments to the function call correspond with those parameters the
values of those arguments are assigned to the properties (otherwise the
assigned value is undefined). Inner function definitions are used to
create function objects which are assigned to properties of the
Variable object with names that correspond to the function name used in
the function declaration. The last stage of variable instantiation is
to create named properties of the Variable object that correspond with
all the local variables declared within the function.

The properties created on the Variable object that correspond with
declared local variables are initially assigned undefined values during
variable instantiation, the actual initialisation of local variables
does not happen until the evaluation of the corresponding assignment
expressions during the execution of the function body code.

It is the fact that the Activation object, with its arguments property,
and the Variable object, with named properties corresponding with
function local variables, are the same object, that allows the
identifier arguments to be treated as if it was a function local
variable.

Jul 23 '05 #20

P: n/a
On 9 Dec 2004 20:00:59 -0800, <lk******@geocities.com> wrote:

[snip]
Reading the article below, (linked to from Cornford's site) I'm curious
if there is ever a time when a Javascript programmer needs to know
anything about the Activation object? Has there ever been a time when
you yourself have needed to use your knowledge of it in any way?
Yes, as it explains some of the behaviour you will observe...
Can I ignore this bit?


....but you probably can get away with ignoring some of the detail, at
least to start with.

Probably the most important bit of information is what the
activation/variable object holds:

- The formal (named) arguments for the function.
- The arguments object.
- Local variables.
- Inner functions defined with

function identifer(...) {...}

or

var identifier = function(...) {...};

In the latter case: an expression assigned to a local variable.

with the most significant being the last item: inner functions. Why? Well,
consider this (admittedly bad) example:

function MyObject() {
/* Define an inner function. Will become
* a property of the activation object.
*/
function myInner() {
return this;
}

/* Define method for the new object. Will
* become a property of that object.
*/
this.myMethod = function() {
return this;
};

/* A test method. It will return an
* object containing two properties:
*
* inner - the result of a call to myInner
* outer - the result of a call to myMethod
*/
this.test = function() {
return {
inner : myInner(),
outer : this.myMethod()
};
};
}

var myObject = new MyObject(),
result = myObject.test();

alert(result.outer == myObject); // true
alert(result.inner == myObject); // false

Notice that although both functions return the this operator, only the
method, myMethod, actually returns a reference to the object, myObject.
The reason is when a function is called, the caller provides the value of
the this operator based on *how* that function is called.

If a method is called as a method:

obj.method()

then the this operator will refer to object (obj, above). However, if a
method is called as a property of the global object (a global function),
or as a property of an activation object (an inner function), then the
this operator will refer to the global object. So, if you go back to the
last line in the example and change it to:

alert(result.inner == window); // or == this);

the message will show true.

I hope that made sense. It seemed a little awkward to explain.

The final point to remember about the activation object is that when a
closure is formed, whether it refers to local variables or functions, or
not, the entire activation object (in fact the entire scope chain) and all
of its properties will be kept in memory. This can be important because if
these properties reference other objects, those objects won't be
considered "collectable" by the garbage collector so you'll keep them in
memory, too. Therefore, it's a good idea to destroy any references you
won't need:

ref = null;

This is also covered in the article, but I thought I'd give it a quick
mention here.

[snip]

If I did a poor job of explaining anything above, even if you understood
my point, do tell me. I'll either have another crack at it (if you want me
to), or I'll try to remember for any future explanations.

Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #21

P: n/a
I just got Danny Goodman's Javascript Bible and it seems to be a good
resource. One thing it seems Javascript lacks (compared to, say, Java)
is a single site that brings together all the DOM information a
programmer might want. Instead, each browser has its own DOM site.
Books about PHP tend to be redundant as they only repeat the info
www.php.net, but Javascript is a language that really needs 3rd - party
efforts at organizing all the language information.

Jul 23 '05 #22

P: n/a
Hi,

lk******@geocities.com wrote:
I just got Danny Goodman's Javascript Bible and it seems to be a good
resource. One thing it seems Javascript lacks (compared to, say, Java)
is a single site that brings together all the DOM information a
programmer might want. Instead, each browser has its own DOM site.
Books about PHP tend to be redundant as they only repeat the info
www.php.net, but Javascript is a language that really needs 3rd - party
efforts at organizing all the language information.


The thing is, the DOM has really nothing to do with JavaScript, and the
DOM is different in each browser, thus a different documentation. Let me
explain.

1) The DOM has nothing to do with javascript: The DOM is a set of
objects (Document Object Model) which allows access to the document.
It's an API, an interface. The fact that you program it with JavaScript
is just because JavaScript is available in browsers. In .NET, you
program the DOM of XML files, with C#, VB.NET, JScript, J#, etc... In
IE, you can use VBScript. So you must decide if you want a JavaScript
guide, describing the language, or a DOM documentation, describing the
objects (and if possible, language independant).

2) The DOM is different in each browser: Yeah, unfortunately, each
browser maker has his own implementation, and they differ. These last
days, we're lucky enough that they don't differ that much, but they do.
Thus one documentation per browser (or environment, or platform, if you
like).

The Java documentation you refer to is not a Java documentation stricto
sensu, it's rather the API documentation of the JVM (a platform). There
is only one, because there is only one API, the one released by Sun. In
fact, there are more, because IE used to have their own implementation,
and their own documentation...

I hope it helps you to understand what you're looking for...

Greetings,

Laurent
--
Laurent Bugnion, GalaSoft
Software engineering: http://www.galasoft-LB.ch
Private/Malaysia: http://mypage.bluewin.ch/lbugnion
Support children in Calcutta: http://www.calcutta-espoir.ch
Jul 23 '05 #23

P: n/a
I'm assuming it is allowed to use the hash-like syntax to recreate the
effects of a hash table, so long as one remembers that one is not
really dealing with a hash table. I'm trying to come up with a function
that will toggle the visibility for all the DIVs on a page. I need an
object to rememeber the different visibility. Is what I do below an
acceptable use of the hash table type syntax?


isDivVisible = new Object();
function hideOrShowDiv(elementPointer) {
var divId = elementPointer.id;
if (document.getElementById(divId)) {
var optionDiv = document.getElementById(divId);

// 12-30-04 - we need isDivVisible to remember a
different
// visibility state for each div on the page, so we
use
// Javascript's hash-like syntax to keep track of
each
// div as if the various states were being stored
in an array
if (isDivVisible.divId) {
if (isDivVisible["divId"] == true) {
optionDiv.style.visibility='hidden';
optionDiv.style.height='0px';
optionDiv.style.width='0px';
optionDiv.style.overflow='auto';
optionDiv.style.display='none';
isDivVisible["divId"] = false;
} else {
optionDiv.style.visibility='visible';
optionDiv.style.height='auto';
optionDiv.style.width='auto';
optionDiv.style.overflow='auto';
optionDiv.style.display='block';
isDivVisible["divId"] = true;

}
} else {
optionDiv.style.visibility='visible';
optionDiv.style.height='auto';
optionDiv.style.width='auto';
optionDiv.style.overflow='auto';
optionDiv.style.display='block';
isDivVisible["divId"] = true;
}
}
}

Jul 23 '05 #24

P: n/a
On 30 Dec 2004 12:04:43 -0800, <lk******@geocities.com> wrote:

Please quote relevant material when you reply to a post. I have no idea
what you're replying to.
I'm assuming it is allowed to use the hash-like syntax to recreate the
effects of a hash table, so long as one remembers that one is not really
dealing with a hash table.
Yes. The important thing is to understand and remember the limitations. If
those limitations don't apply then there's no reason to go through the
hassle of implementing a proper hash table.

[snip]
Is what I do below an acceptable use of the hash table type syntax?
Almost, though it could be made a little more robust, however the specific
syntax you use is wrong. You also seem to be performing some unnecessary
element reference -> id -> element reference operations again.
isDivVisible = new Object();
I don't like the name, isDivVisible. Names like that (ones which contain
'is' or 'has') should be reserved for functions because they "answer"
questions by returning a value. Variables don't "do" anything.
function hideOrShowDiv(elementPointer) {
By 'elementPointer', I assume you mean a reference[1] to a HTML element.
var divId = elementPointer.id;
if (document.getElementById(divId)) {
var optionDiv = document.getElementById(divId);
If you passed a reference to the function, why are you getting the id and
then the reference again? You did this once before - I would have hoped
you'd remember not to do it again.
// 12-30-04 - we need isDivVisible to remember a
different
// visibility state for each div on the page, so we
use
// Javascript's hash-like syntax to keep track of
each
// div as if the various states were being stored
in an array
It's best to make sure that code posted to a newsgroup can be copied
without alteration. With comments like the one above, I'd suggest you use
a multiline (/*...*/) comment rather than several single line ones.

Assuming the line below did what you intended it to...
if (isDivVisible.divId) {
The else block for the inner if..else statement below will never be
executed. Think about it: the (incorrect) expression above doesn't
determine whether the property is defined, just whether it evaluates to
true or false. The sort of test you're looking for is a typeof analysis.

Killing two birds with one stone:

if('boolean' == typeof isDivVisible[divId]) {

Notice that you were using 'divId' literally, rather than the value it
contained. As for the typeof test, this makes more sense: if you defined
the property yourself, it will either be true or false (a boolean). If the
property is defined, but it's not a boolean, then the property was
predefined (by the object's prototype).
if (isDivVisible["divId"] == true) {
optionDiv.style.visibility='hidden';
optionDiv.style.height='0px';
optionDiv.style.width='0px';
optionDiv.style.overflow='auto';
optionDiv.style.display='none';
This is excessive. If you're trying to hide an element and collapse the
space it occupies, just use the display property.
isDivVisible["divId"] = false;
} else {
optionDiv.style.visibility='visible';
optionDiv.style.height='auto';
optionDiv.style.width='auto';
optionDiv.style.overflow='auto';
optionDiv.style.display='block';
Assuming that the page stylesheet doesn't hide any DIV elements initially,
you could simply assign an empty string to the display property to restore
the DIV.
isDivVisible["divId"] = true;


[snip]

Overall, the script could be condensed to:

var divs = {};

function toggleDiv(ref) {var id = ref.id, value = divs[id];
if(!ref.style) {return;}
if('boolean' == typeof value) {
/* If the DIV is visible, set the display property to 'none'. */
ref.style.display = value ? 'none' : 'block';
/* Toggle the value in the hash table. */
divs[id] = !value;
} else {
/* What you do here depends on what you'd expect if the entry
* in the hash table was undefined. If the DIV would be hidden
* then you could use:
*/
divs[id] = false;
toggleDiv(ref);
}
}

Depending on what is actually happening in your page, you could make this
a lot easier.

In the simplest case, the display property is only set in one of two ways:
via the style attribute on the element itself, or the style object. In
other words, the display cannot be affected through a class or some other
mechanism in a page style sheet. Assuming you meet this criteria, you
could inspect the style object itself, rather than use an object to
contain the state of each DIV:

function toggleDiv(ref) {
if((ref = ref.style)) {
ref.display = ('none' == ref.display) ? '' : 'none';
}
}

On the other hand, if you're in a more complicated situation, then you can
obtain the computed value of the display property. It's pretty much the
same as the above except determining the current value is a little more
difficult (especially as IE requires its own code path).

function getComputedStyle(obj) {var dV = document.defaultView;
if(!obj || ('object' != typeof obj)) {return null;}
return(getComputedStyle = (dV && dV.getComputedStyle) ?
function(obj) {return dV.getComputedStyle(obj, null);}
: ((dV = null) || obj.currentStyle) ?
function(obj) {return obj.currentStyle;}
: function() {return null;})(obj);
}

function toggleDiv(ref) {var cS;
if((cS = getComputedStyle(ref)) && (ref = ref.style)) {
ref.display = ('none' == cS.display) ? 'block' : 'none';
}
}

(Untested)

Hope that helps,
Mike
[1] There are no pointers in ECMAScript, only references, despite what
Microsoft's documentation might suggest.

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #25

P: n/a
In article <opsjv499dbx13kvk@atlantis>,
"Michael Winter" <M.******@blueyonder.co.invalid> wrote:
On 30 Dec 2004 12:04:43 -0800, <lk******@geocities.com> wrote:

isDivVisible = new Object();


I don't like the name, isDivVisible. Names like that (ones which contain
'is' or 'has') should be reserved for functions because they "answer"
questions by returning a value. Variables don't "do" anything.


I'm with you, but then how do you name boolean variables, like
a "trace" flag, so that

if (booleanVar) {

reads clearly?
Jul 23 '05 #26

P: n/a
On Mon, 03 Jan 2005 14:24:23 -0600, Chris Riesbeck <cr*******@yahoo.com>
wrote:
[...] how do you name boolean variables, like a "trace" flag, so that

if (booleanVar) {

reads clearly?


It would depend on the purpose. Certainly for most variables, the
adjective itself (like visible) should suffice. I'm terrible at thinking
of things on the spot though, so I can't currently come up with an
exception. Perhaps you can think of a troublesome name.

Mike

--
Michael Winter
Replace ".invalid" with ".uk" to reply by e-mail.
Jul 23 '05 #27

This discussion thread is closed

Replies have been disabled for this discussion.