CodeSnip: Generic Lists, not just a .NET thing
page 1 of 2
Published: 19 Sep 2007
Abstract
In this article Ryan creates a snippet library that brings the generic list functionality from .NET into JavaScript.
by Ryan Scott
Feedback
Average Rating: This article has not yet been rated.
Views (Total / Last 10 Days): 14388/ 23
Article Contents:

Introduction

The Generic class is a strongly typed list of objects that can be easily referenced by index. Many .NET developers benefit from the Generic class because they are easily searched, sorted, and manipulated.

I find myself developing in JavaScript from an object orientated perspective, even though it is more of a procedural language, with influences of C# leaving its trace. I first started with this generic class below and started noticing great benefits: the code is more easily readable, .NET developers who are not familiar with JavaScript tend to not have problems learning when they can code similar to C#, and code re-usability.

Listing 1

//--------------------------------------------------------------
// Class: List
// Author: Ryan Estes
// Description: Contructs an object that references a collection
//              of objects.
// Methods: Add,Contains,Count,Find,FindIndex,FindAll,Items,GetRange,Sort,Reverse,
//          GetRange,Remove,RemoveAll,ToString, GetType, Equals,Concat
//
//---------------------------------------------------------------
 
// Constructor: (),(Object obj)
function List()
{
   this._arrItems = (arguments.length == 1)? new Array(arguments[0]) : new Array();
   
   // Param: (Object obj)
   // Return: void
   this.Add = function(obj) {
      this._arrItems[this._arrItems.length] = obj;
   }
   
   // Property : Accessor
   this.Count = function() {
      return this._arrItems.length;
   }
   
   // Param: (List<T>)
   // Return: void
   this.Concat = function() {
       try
       {
          if(objlist.GetType() != "Library.List")
          {
             throw "(Exception: List_Concat_0) Object of Library.List type expected";
          }
          this._arrItems = this._arrItems.concat(objlist.Items());
       }
       catch (e)
       {
          throw "(Exception: List_Concat_1) Invalid paramter type";
       }
   }
   
   // Param: string
   // Return: boolean
   this.Contains = function(str) {
       for(var i = 0; i < this._arrItems.length; i++)
       {
           alert(str);
           alert(this._arrItems[i]);
           if(str == this._arrItems[i])
              return true;
       }
      return false;
   }
   
 
   this.Equals = function(oList) {
        try
        {
           if(oList.GetType() == this.GetType())
           {
              if(this._arrItems.length == oList.Items().length)
              {
                 for(i = 0; i < this._arrItems.length; i++)
                 {
                    if(this._arrItems[i] != oList.Items()[i])
                    {
                       return false;
                    }
                 }
                 return true;
              }
           }
        }
        catch (e)
        {
           throw "(Exception: List_Equals_0) Invalid parameter type";
        }
        return false;
   }
   
   // Params: Predicate<T>
   // Return: int
   // Description: Returns the number of occurrences
   this.Find = function(pfnc) {
       var intOccurences = 0;
       for(var i = 0; i < this._arrItems.length; i++)
       {
          try
          {
              if(pfnc(this._arrItems[i]))
              {
                 intOccurences++;
              }
          }
          catch (e)
          {
             throw "(Exception: List_Find_0) " + e.message;
          }
       }
      return intOccurences;
   }
   
   // Params: Predicate<T>
   // Return: int
   // Description: Returns the index of the first occurrence
   this.FindIndex = function(pfnc) {
       for(i = 0; i < this._arrItems.length; i++)
       {
          try
          {
              if(pfnc(this._arrItems[i]))
              {
                 return i;
              }
          }
          catch (e)
          {
             throw "(Exception: List_FindIndex_0) " + e.message;
          }
       }
      return -1;
   }
   
   
   
   // Params: Predicate<T>
   // Return: List<Object>
   // Description: Returns a list of matching objects
   this.FindAll = function(pfnc) {
       var objList = new List();
       for(var i = 0; i < this._arrItems.length; i++)
       {
          try
          {
              if(pfnc(this._arrItems[i]))
              {
                 objList.Add(this._arrItems[i]);
              }
          }
          catch (e)
          {
             throw "(Exception: List_FindAll_0) " + e.message;
          }
       }
      return objList;
   }
      
   // Return: List<Object>
   // Description: Returns a partition of a list.
   this.GetRange = function(intStartIndex,intCount) {
       var intEndIndex = intStartIndex + (intCount - 1) ;
       var objlist = new List();
       if(intStartIndex < 0 || intEndIndex < 0)
          throw "(Exception: List_GetRange_0) Index must be a non-negative integer";
       if(intEndIndex > this._arrItems.length - 1)
          throw "(Exception: List_GetRange_1) Index Out of Range";
       if(intStartIndex > intEndIndex)
          throw "(Exception: List_GetRange_2)" +
                     " Start index must be less than or equal to the end index";
       for(var i = intStartIndex; i < intEndIndex + 1; i++)
       {
          objlist.Add(this._arrItems[i]);
       }
       return objlist;
   }
   
   this.GetType = function() {
      return "Library.List";
   }
   
   // Property : Accessor
   this.Items = function() {
      return this._arrItems;
   }
   
   // Return: void
   this.Reverse = function() {
      this._arrItems = this._arrItems.reverse()
   }
   
   // Return: void
   this.Remove = function(intIndex) {
       if(intIndex < 0)
         throw "(Exception: List_Remove_0) Index must be a non-negative integer";
       if(intIndex > this._arrItems.length) 
         throw "(Exception: List_Remove_1) Index Out of Range"; 
       var olist = new List();
       for(var i = 0; i < this._arrItems.length; i++)
       {
         if(i != intIndex)
           olist.Add(this._arrItems[i]);
       }
       this._arrItems = olist.Items();
   }
   
   // Return: void
   this.RemoveAll = function() {
      this._arrItems = new Array();
   }
   
   // Return: void
   this.Sort = function() {
      this._arrItems = this._arrItems.sort();
   }
   
   // Params: (), (string delimiter)
   this.ToString = function() {
       var strDelimiter = (arguments.length == 1)? arguments[0] : "";
       return this._arrItems.join(strDelimiter);
   }
}

There you have it, the generic class in a JavaScript nutshell. For clarification, below are some samples of how this class can be used.

Listing 2

var oList1 = new List();
// Count()
alert(oList1.Count());
 
// Add()
oList1.Add("ASP");
oList1.Add("DOT");
oList1.Add("NET");
alert(oList1.Count());
 
var oList2 = new List("ASP");
// Equals()
alert(oList1.Equals(oList2));
 
// GetType()
alert(oList2.GetType() == oList1.GetType());
 
// Reverse()
alert(oList1.Reverse());
 
//  Find()
var fNumberOfASP = function(str) {
     return str == "ASP";
}
alert(oList1.Find(fNumberOfASP) + "" );
 
// List of Objects
function Coordinate(intX,intY)
{
    this.X = intX;
    this.Y = intY;
}
 
var oList3 = new List();
oList3.Add(new Coordinate(0,0));
oList3.Add(new Coordinate(1,1));
 
alert(oList3.GetRange(0,1).Count());

View Entire Article

User Comments

No comments posted yet.

Product Spotlight
Product Spotlight 





Community Advice: ASP | SQL | XML | Regular Expressions | Windows


©Copyright 1998-2024 ASPAlliance.com  |  Page Processed at 2024-04-19 10:11:56 PM  AspAlliance Recent Articles RSS Feed
About ASPAlliance | Newsgroups | Advertise | Authors | Email Lists | Feedback | Link To Us | Privacy | Search