diff options
| author | mensonge <mensonge@b3834d28-1941-0410-a4f8-b48e95affb8f> | 2008-11-13 09:49:11 +0000 | 
|---|---|---|
| committer | mensonge <mensonge@b3834d28-1941-0410-a4f8-b48e95affb8f> | 2008-11-13 09:49:11 +0000 | 
| commit | e44a7e37b6c7b5961adaffc62b9042b8d442938e (patch) | |
| tree | 95b67c356e93163467db2451f2b8cce84ed5d582 /includes/js/dojox/lang | |
| parent | a62b9742ee5e28bcec6872d88f50f25b820914f6 (diff) | |
| download | semanticscuttle-e44a7e37b6c7b5961adaffc62b9042b8d442938e.tar.gz semanticscuttle-e44a7e37b6c7b5961adaffc62b9042b8d442938e.tar.bz2  | |
New feature: basic Ajax suggestion for tags and implementation of Dojo toolkit
git-svn-id: https://semanticscuttle.svn.sourceforge.net/svnroot/semanticscuttle/trunk@151 b3834d28-1941-0410-a4f8-b48e95affb8f
Diffstat (limited to 'includes/js/dojox/lang')
23 files changed, 1339 insertions, 0 deletions
diff --git a/includes/js/dojox/lang/LICENSE b/includes/js/dojox/lang/LICENSE new file mode 100644 index 0000000..d84a6aa --- /dev/null +++ b/includes/js/dojox/lang/LICENSE @@ -0,0 +1,21 @@ +The MIT License + +Copyright (c) 2007 Oliver Steele + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/includes/js/dojox/lang/README b/includes/js/dojox/lang/README new file mode 100644 index 0000000..753b943 --- /dev/null +++ b/includes/js/dojox/lang/README @@ -0,0 +1,37 @@ +------------------------------------------------------------------------------- +dojox.lang +------------------------------------------------------------------------------- +Version 0.991 +Release date: 07/30/2007 +------------------------------------------------------------------------------- +Project state: +[beta] +------------------------------------------------------------------------------- +Credits +	Eugene Lazutkin (eugene.lazutkin@gmail.com) +------------------------------------------------------------------------------- +Project description + +Implementation of common functional operations, and provisions +Later we can add other JS language-related helpers. +------------------------------------------------------------------------------- +Dependencies: + +None. +------------------------------------------------------------------------------- +Documentation + +------------------------------------------------------------------------------- +Installation instructions + +Grab the following from the Dojo SVN Repository: +http://svn.dojotoolkit.org/var/src/dojo/dojox/trunk/lang/* + +Install into the following directory structure: +/dojox/lang/ + +...which should be at the same level as your Dojo checkout. +------------------------------------------------------------------------------- +Additional Notes + +See tests and the source for more details. diff --git a/includes/js/dojox/lang/functional.js b/includes/js/dojox/lang/functional.js new file mode 100644 index 0000000..e75ad00 --- /dev/null +++ b/includes/js/dojox/lang/functional.js @@ -0,0 +1,9 @@ +if(!dojo._hasResource["dojox.lang.functional"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional"] = true; +dojo.provide("dojox.lang.functional"); + +dojo.require("dojox.lang.functional.lambda"); +dojo.require("dojox.lang.functional.array"); +dojo.require("dojox.lang.functional.object"); + +} diff --git a/includes/js/dojox/lang/functional/array.js b/includes/js/dojox/lang/functional/array.js new file mode 100644 index 0000000..45c2613 --- /dev/null +++ b/includes/js/dojox/lang/functional/array.js @@ -0,0 +1,113 @@ +if(!dojo._hasResource["dojox.lang.functional.array"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.array"] = true; +dojo.provide("dojox.lang.functional.array"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- array-processing functions similar to standard JS functions + +// Notes: +//	- this module provides JS standard methods similar to high-level functions in dojo/_base/array.js:  +//		forEach, map, filter, every, some + +// Defined methods: +//	- take any valid lambda argument as the functional argument +//	- operate on dense arrays +//	- take a string as the array argument +//	- take an iterator objects as the array argument + +(function(){ +	var d = dojo, df = dojox.lang.functional; + +	d.mixin(df, { +		// JS 1.6 standard array functions, which can take a lambda as a parameter. +		// Consider using dojo._base.array functions, if you don't need the lambda support. +		filter: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: creates a new array with all elements that pass the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var t = [], v; +			if(d.isArray(a)){ +				for(var i = 0, n = a.length; i < n; ++i){ +					v = a[i]; +					if(f.call(o, v, i, a)){ t.push(v); } +				} +			}else{ +				for(var i = 0; a.hasNext();){ +					v = a.next(); +					if(f.call(o, v, i++)){ t.push(v); } +				} +			} +			return t;	// Array +		}, +		forEach: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: executes a provided function once per array element. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			if(d.isArray(a)){ +				for(var i = 0, n = a.length; i < n; f.call(o, a[i], i, a), ++i); +			}else{ +				for(var i = 0; a.hasNext(); f.call(o, a.next(), i++)); +			} +		}, +		map: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: creates a new array with the results of calling  +			//	a provided function on every element in this array. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var t, n; +			if(d.isArray(a)){ +				t = new Array(n = a.length); +				for(var i = 0; i < n; t[i] = f.call(o, a[i], i, a), ++i); +			}else{ +				t = []; +				for(var i = 0; a.hasNext(); t.push(f.call(o, a.next(), i++))); +			} +			return t;	// Array +		}, +		every: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: tests whether all elements in the array pass the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			if(d.isArray(a)){ +				for(var i = 0, n = a.length; i < n; ++i){ +					if(!f.call(o, a[i], i, a)){ +						return false;	// Boolean +					} +				} +			}else{ +				for(var i = 0; a.hasNext();){ +					if(!f.call(o, a.next(), i++)){ +						return false;	// Boolean +					} +				} +			} +			return true;	// Boolean +		}, +		some: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: tests whether some element in the array passes the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			if(d.isArray(a)){ +				for(var i = 0, n = a.length; i < n; ++i){ +					if(f.call(o, a[i], i, a)){ +						return true;	// Boolean +					} +				} +			}else{ +				for(var i = 0; a.hasNext();){ +					if(f.call(o, a.next(), i++)){ +						return true;	// Boolean +					} +				} +			} +			return false;	// Boolean +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/curry.js b/includes/js/dojox/lang/functional/curry.js new file mode 100644 index 0000000..7c795ec --- /dev/null +++ b/includes/js/dojox/lang/functional/curry.js @@ -0,0 +1,96 @@ +if(!dojo._hasResource["dojox.lang.functional.curry"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.curry"] = true; +dojo.provide("dojox.lang.functional.curry"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- currying and partial functions +//	- argument pre-processing: mixer and flip + +// Acknoledgements: +//	- partial() is based on work by Oliver Steele  +//		(http://osteele.com/sources/javascript/functional/functional.js) +//		which was published under MIT License + +// Defined methods: +//	- take any valid lambda argument as the functional argument + +(function(){ +	var df = dojox.lang.functional; + +	var currying = function(/*Object*/ info){ +		return function(){	// Function +			if(arguments.length + info.args.length < info.arity){ +				return currying({func: info.func, arity: info.arity,  +					args: Array.prototype.concat.apply(info.args, arguments)}); +			} +			return info.func.apply(this, Array.prototype.concat.apply(info.args, arguments)); +		}; +	}; + +	dojo.mixin(df, { +		// currying and partial functions +		curry: function(/*Function|String|Array*/ f, /*Number?*/ arity){ +			// summary: curries a function until the arity is satisfied, at  +			//	which point it returns the calculated value. +			f = df.lambda(f); +			arity = typeof arity == "number" ? arity : f.length; +			return currying({func: f, arity: arity, args: []});	// Function +		}, +		arg: {},	// marker for missing arguments +		partial: function(/*Function|String|Array*/ f){ +			// summary: creates a function where some arguments are bound, and +			//	some arguments (marked as dojox.lang.functional.arg) are will be  +			//	accepted by the final function in the order they are encountered. +			// description: This method is used to produce partially bound  +			//	functions. If you want to change the order of arguments, use +			//	dojox.lang.functional.mixer() or dojox.lang.functional.flip(). +			var a = arguments, args = new Array(a.length - 1), p = []; +			f = df.lambda(f); +			for(var i = 1; i < a.length; ++i){ +				var t = a[i]; +				args[i - 1] = t; +				if(t == df.arg){ +					p.push(i - 1); +				} +			} +			return function(){	// Function +				var t = Array.prototype.slice.call(args, 0); // clone the array +				for(var i = 0; i < p.length; ++i){ +					t[p[i]] = arguments[i]; +				} +				return f.apply(this, t); +			}; +		}, +		// argument pre-processing +		mixer: function(/*Function|String|Array*/ f, /*Array*/ mix){ +			// summary: changes the order of arguments using an array of +			//	numbers mix --- i-th argument comes from mix[i]-th place +			//	of supplied arguments. +			f = df.lambda(f); +			return function(){	// Function +				var t = new Array(mix.length); +				for(var i = 0; i < mix.length; ++i){ +					t[i] = arguments[mix[i]]; +				} +				return f.apply(this, t); +			}; +		}, +		flip: function(/*Function|String|Array*/ f){ +			// summary: changes the order of arguments by reversing their +			//	order. +			f = df.lambda(f); +			return function(){	// Function +				// reverse arguments +				var a = arguments, l = a.length - 1, t = new Array(l + 1), i; +				for(i = 0; i <= l; ++i){ +					t[l - i] = a[i]; +				} +				return f.apply(this, t); +			}; +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/fold.js b/includes/js/dojox/lang/functional/fold.js new file mode 100644 index 0000000..90a9a3d --- /dev/null +++ b/includes/js/dojox/lang/functional/fold.js @@ -0,0 +1,87 @@ +if(!dojo._hasResource["dojox.lang.functional.fold"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.fold"] = true; +dojo.provide("dojox.lang.functional.fold"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- "fold" family of functions + +// Notes: +//	- missing high-level functions are provided with the compatible API:  +//		foldl, foldl1, foldr, foldr1 +//	- missing JS standard functions are provided with the compatible API:  +//		reduce, reduceRight + +// Defined methods: +//	- take any valid lambda argument as the functional argument +//	- operate on dense arrays +//	- take a string as the array argument +//	- take an iterator objects as the array argument (only foldl, foldl1, and reduce) + +(function(){ +	var d = dojo, df = dojox.lang.functional; + +	d.mixin(df, { +		// classic reduce-class functions +		foldl: function(/*Array|String|Object*/ a, /*Function*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from left  +			//	to right using a seed value as a starting point; returns the final  +			//	value. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			if(d.isArray(a)){ +				for(var i = 0, n = a.length; i < n; z = f.call(o, z, a[i], i, a), ++i); +			}else{ +				for(var i = 0; a.hasNext(); z = f.call(o, z, a.next(), i++)); +			} +			return z;	// Object +		}, +		foldl1: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from left  +			//	to right; returns the final value. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var z; +			if(d.isArray(a)){ +				z = a[0]; +				for(var i = 1, n = a.length; i < n; z = f.call(o, z, a[i], i, a), ++i); +			}else if(a.hasNext()){ +				z = a.next(); +				for(var i = 1; a.hasNext(); z = f.call(o, z, a.next(), i++)); +			} +			return z;	// Object +		}, +		foldr: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from right +			//	to left using a seed value as a starting point; returns the final  +			//	value. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			for(var i = a.length; i > 0; --i, z = f.call(o, z, a[i], i, a)); +			return z;	// Object +		}, +		foldr1: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from right +			//	to left; returns the final value. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var n = a.length, z = a[n - 1]; +			for(var i = n - 1; i > 0; --i, z = f.call(o, z, a[i], i, a)); +			return z;	// Object +		}, +		// JS 1.8 standard array functions, which can take a lambda as a parameter. +		reduce: function(/*Array|String|Object*/ a, /*Function*/ f, /*Object?*/ z){ +			// summary: apply a function simultaneously against two values of the array  +			//	(from left-to-right) as to reduce it to a single value. +			return arguments.length < 3 ? df.foldl1(a, f) : df.foldl(a, f, z);	// Object +		}, +		reduceRight: function(/*Array|String*/ a, /*Function*/ f, /*Object?*/ z){ +			// summary: apply a function simultaneously against two values of the array  +			//	(from right-to-left) as to reduce it to a single value. +			return arguments.length < 3 ? df.foldr1(a, f) : df.foldr(a, f, z);	// Object +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/lambda.js b/includes/js/dojox/lang/functional/lambda.js new file mode 100644 index 0000000..60be9f3 --- /dev/null +++ b/includes/js/dojox/lang/functional/lambda.js @@ -0,0 +1,110 @@ +if(!dojo._hasResource["dojox.lang.functional.lambda"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.lambda"] = true; +dojo.provide("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- anonymous functions built from the string + +// Acknoledgements: +//	- lambda() is based on work by Oliver Steele  +//		(http://osteele.com/sources/javascript/functional/functional.js) +//		which was published under MIT License + +// Notes: +//	- lambda() produces functions, which after the compilation step are  +//		as fast as regular JS functions (at least theoretically). + +// Lambda input values: +//	- returns functions unchanged +//	- converts strings to functions +//	- converts arrays to a functional composition + +(function(){ +	var df = dojox.lang.functional; + +	// split() is augmented on IE6 to ensure the uniform behavior +	var split = "ab".split(/a*/).length > 1 ? String.prototype.split : +			function(sep){ +				 var r = this.split.call(this, sep), +					 m = sep.exec(this); +				 if(m && m.index == 0){ r.unshift(""); } +				 return r; +			}; +			 +	var lambda = function(/*String*/ s){ +		var args = [], sects = split.call(s, /\s*->\s*/m); +		if(sects.length > 1){ +			while(sects.length){ +				s = sects.pop(); +				args = sects.pop().split(/\s*,\s*|\s+/m); +				if(sects.length){ sects.push("(function(" + args + "){return (" + s + ")})"); } +			} +		}else if(s.match(/\b_\b/)){ +			args = ["_"]; +		}else{ +			var l = s.match(/^\s*(?:[+*\/%&|\^\.=<>]|!=)/m), +				r = s.match(/[+\-*\/%&|\^\.=<>!]\s*$/m); +			if(l || r){ +				if(l){ +					args.push("$1"); +					s = "$1" + s; +				} +				if(r){ +					args.push("$2"); +					s = s + "$2"; +				} +			}else{ +				// the point of the long regex below is to exclude all well-known  +				// lower-case words from the list of potential arguments +				var vars = s. +					replace(/(?:\b[A-Z]|\.[a-zA-Z_$])[a-zA-Z_$\d]*|[a-zA-Z_$][a-zA-Z_$\d]*:|this|true|false|null|undefined|typeof|instanceof|in|delete|new|void|arguments|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|escape|eval|isFinite|isNaN|parseFloat|parseInt|unescape|dojo|dijit|dojox|window|document|'(?:[^'\\]|\\.)*'|"(?:[^"\\]|\\.)*"/g, ""). +					match(/([a-z_$][a-z_$\d]*)/gi) || []; +				var t = {}; +				dojo.forEach(vars, function(v){ +					if(!(v in t)){ +						args.push(v); +						t[v] = 1; +					} +				}); +			} +		} +		return {args: args, body: "return (" + s + ");"};	// Object +	}; + +	var compose = function(/*Array*/ a){ +		return a.length ?  +					function(){ +						var i = a.length - 1, x = df.lambda(a[i]).apply(this, arguments); +						for(--i; i >= 0; --i){ x = df.lambda(a[i]).call(this, x); } +						return x; +					} +				:  +					// identity +					function(x){ return x; }; +	}; + +	dojo.mixin(df, { +		// lambda +		buildLambda: function(/*String*/ s){ +			// summary: builds a function from a snippet, returns a string,  +			//	which represents the function. +			// description: This method returns a textual representation of a function  +			//	built from the snippet. It is meant to be evaled in the proper context,  +			//	so local variables can be pulled from the environment. +			s = lambda(s); +			return "function(" + s.args.join(",") + "){" + s.body + "}";	// String +		}, +		lambda: function(/*Function|String|Array*/ s){ +			// summary: builds a function from a snippet, or array (composing), returns  +			//	a function object; functions are passed through unmodified. +			// description: This method is used to normalize a functional representation +			//	(a text snippet, an array, or a function) to a function object. +			if(typeof s == "function"){ return s; } +			if(s instanceof Array){ return compose(s); } +			s = lambda(s); +			return new Function(s.args, s.body);	// Function +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/listcomp.js b/includes/js/dojox/lang/functional/listcomp.js new file mode 100644 index 0000000..adb4883 --- /dev/null +++ b/includes/js/dojox/lang/functional/listcomp.js @@ -0,0 +1,54 @@ +if(!dojo._hasResource["dojox.lang.functional.listcomp"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.listcomp"] = true; +dojo.provide("dojox.lang.functional.listcomp"); + +// This module adds high-level functions and related constructs: +//	- list comprehensions similar to JavaScript 1.7 + +// Notes: +//	- listcomp() produces functions, which after the compilation step are  +//		as fast as regular JS functions (at least theoretically). + +(function(){ +	var g_re = /\bfor\b|\bif\b/gm; + +	var listcomp = function(/*String*/ s){ +		var frag = s.split(g_re), act = s.match(g_re), +			head = ["var r = [];"], tail = []; +		for(var i = 0; i < act.length;){ +			var a = act[i], f = frag[++i]; +			if(a == "for" && !/^\s*\(\s*(;|var)/.test(f)){ +				f = f.replace(/^\s*\(/, "(var "); +			} +			head.push(a, f, "{"); +			tail.push("}"); +		} +		return head.join("") + "r.push(" + frag[0] + ");" + tail.join("") + "return r;";	// String +	}; + +	dojo.mixin(dojox.lang.functional, { +		buildListcomp: function(/*String*/ s){ +			// summary: builds a function from a text snippet, which represents a valid +			//	JS 1.7 list comprehension, returns a string, which represents the function. +			// description: This method returns a textual representation of a function  +			//	built from the list comprehension text snippet (conformant to JS 1.7).  +			//	It is meant to be evaled in the proper context, so local variable can be  +			//	pulled from the environment. +			return "function(){" + listcomp(s) + "}";	// String +		}, +		compileListcomp: function(/*String*/ s){ +			// summary: builds a function from a text snippet, which represents a valid +			//	JS 1.7 list comprehension, returns a function object. +			// description: This method returns a function built from the list  +			//	comprehension text snippet (conformant to JS 1.7). It is meant to be  +			//	reused several times. +			return new Function([], listcomp(s));	// Function +		}, +		listcomp: function(/*String*/ s){ +			// summary: executes the list comprehension building an array. +			return (new Function([], listcomp(s)))();	// Array +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/object.js b/includes/js/dojox/lang/functional/object.js new file mode 100644 index 0000000..52b6272 --- /dev/null +++ b/includes/js/dojox/lang/functional/object.js @@ -0,0 +1,48 @@ +if(!dojo._hasResource["dojox.lang.functional.object"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.object"] = true; +dojo.provide("dojox.lang.functional.object"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- object/dictionary helpers + +// Defined methods: +//	- take any valid lambda argument as the functional argument + +(function(){ +	var d = dojo, df = dojox.lang.functional, empty = {}; + +	d.mixin(df, { +		// object helpers +		forIn: function(/*Object*/ obj, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: iterates over all object members skipping members, which  +			//	are present in the empty object (IE and/or 3rd-party libraries). +			o = o || d.global; f = df.lambda(f); +			for(var i in obj){ +				if(i in empty){ continue; } +				f.call(o, obj[i], i, obj); +			} +		}, +		keys: function(/*Object*/ obj){ +			// summary: returns an array of all keys in the object +			var t = []; +			for(var i in obj){ +				if(i in empty){ continue; } +				t.push(i); +			} +			return	t; // Array +		}, +		values: function(/*Object*/ obj){ +			// summary: returns an array of all values in the object +			var t = []; +			for(var i in obj){ +				if(i in empty){ continue; } +				t.push(obj[i]); +			} +			return	t; // Array +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/reversed.js b/includes/js/dojox/lang/functional/reversed.js new file mode 100644 index 0000000..4375948 --- /dev/null +++ b/includes/js/dojox/lang/functional/reversed.js @@ -0,0 +1,79 @@ +if(!dojo._hasResource["dojox.lang.functional.reversed"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.reversed"] = true; +dojo.provide("dojox.lang.functional.reversed"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- reversed versions of array-processing functions similar to standard JS functions + +// Notes: +//	- this module provides reversed versions of standard array-processing functions:  +//		forEachRev, mapRev, filterRev + +// Defined methods: +//	- take any valid lambda argument as the functional argument +//	- operate on dense arrays +//	- take a string as the array argument + +(function(){ +	var d = dojo, df = dojox.lang.functional; + +	d.mixin(df, { +		// JS 1.6 standard array functions, which can take a lambda as a parameter. +		// Consider using dojo._base.array functions, if you don't need the lambda support. +		filterRev: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: creates a new array with all elements that pass the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var t = [], v; +			for(var i = a.length - 1; i >= 0; --i){ +				v = a[i]; +				if(f.call(o, v, i, a)){ t.push(v); } +			} +			return t;	// Array +		}, +		forEachRev: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: executes a provided function once per array element. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			for(var i = a.length - 1; i >= 0; f.call(o, a[i], i, a), --i); +		}, +		mapRev: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: creates a new array with the results of calling  +			//	a provided function on every element in this array. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var n = a.length, t = new Array(n); +			for(var i = n - 1, j = 0; i >= 0; t[j++] = f.call(o, a[i], i, a), --i); +			return t;	// Array +		}, +		everyRev: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: tests whether all elements in the array pass the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			for(var i = a.length - 1; i >= 0; --i){ +				if(!f.call(o, a[i], i, a)){ +					return false;	// Boolean +				} +			} +			return true;	// Boolean +		}, +		someRev: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: tests whether some element in the array passes the test  +			//	implemented by the provided function. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			for(var i = a.length - 1; i >= 0; --i){ +				if(f.call(o, a[i], i, a)){ +					return true;	// Boolean +				} +			} +			return false;	// Boolean +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/scan.js b/includes/js/dojox/lang/functional/scan.js new file mode 100644 index 0000000..65a3ef2 --- /dev/null +++ b/includes/js/dojox/lang/functional/scan.js @@ -0,0 +1,84 @@ +if(!dojo._hasResource["dojox.lang.functional.scan"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.scan"] = true; +dojo.provide("dojox.lang.functional.scan"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- "scan" family of functions + +// Notes: +//	- missing high-level functions are provided with the compatible API:  +//		scanl, scanl1, scanr, scanr1 + +// Defined methods: +//	- take any valid lambda argument as the functional argument +//	- operate on dense arrays +//	- take a string as the array argument +//	- take an iterator objects as the array argument (only scanl, and scanl1) + +(function(){ +	var d = dojo, df = dojox.lang.functional; + +	d.mixin(df, { +		// classic reduce-class functions +		scanl: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from left  +			//	to right using a seed value as a starting point; returns an array +			//	of values produced by foldl() at that point. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var t, n; +			if(d.isArray(a)){ +				t = new Array((n = a.length) + 1); +				t[0] = z; +				for(var i = 0; i < n; z = f.call(o, z, a[i], i, a), t[++i] = z); +			}else{ +				t = [z]; +				for(var i = 0; a.hasNext(); t.push(z = f.call(o, z, a.next(), i++))); +			} +			return t;	// Array +		}, +		scanl1: function(/*Array|String|Object*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from left  +			//	to right; returns an array of values produced by foldl1() at that  +			//	point. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var t, n, z; +			if(d.isArray(a)){ +				t = new Array(n = a.length); +				t[0] = z = a[0]; +				for(var i = 1; i < n; t[i] = z = f.call(o, z, a[i], i, a), ++i); +			}else if(a.hasNext()){ +				t = [z = a.next()]; +				for(var i = 1; a.hasNext(); t.push(z = f.call(o, z, a.next(), i++))); +			} +			return t;	// Array +		}, +		scanr: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from right +			//	to left using a seed value as a starting point; returns an array +			//	of values produced by foldr() at that point. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var n = a.length, t = new Array(n + 1); +			t[n] = z; +			for(var i = n; i > 0; --i, z = f.call(o, z, a[i], i, a), t[i] = z); +			return t;	// Array +		}, +		scanr1: function(/*Array|String*/ a, /*Function|String|Array*/ f, /*Object?*/ o){ +			// summary: repeatedly applies a binary function to an array from right +			//	to left; returns an array of values produced by foldr1() at that  +			//	point. +			if(typeof a == "string"){ a = a.split(""); } +			o = o || d.global; f = df.lambda(f); +			var n = a.length, t = new Array(n), z = a[n - 1]; +			t[n - 1] = z; +			for(var i = n - 1; i > 0; --i, z = f.call(o, z, a[i], i, a), t[i] = z); +			return t;	// Array +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/sequence.js b/includes/js/dojox/lang/functional/sequence.js new file mode 100644 index 0000000..c5aaa1c --- /dev/null +++ b/includes/js/dojox/lang/functional/sequence.js @@ -0,0 +1,38 @@ +if(!dojo._hasResource["dojox.lang.functional.sequence"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.sequence"] = true; +dojo.provide("dojox.lang.functional.sequence"); + +dojo.require("dojox.lang.functional.lambda"); + +// This module adds high-level functions and related constructs: +//	- sequence generators + +// Defined methods: +//	- take any valid lambda argument as the functional argument + +(function(){ +	var d = dojo, df = dojox.lang.functional; + +	d.mixin(df, { +		// sequence generators +		repeat: function(/*Number*/ n, /*Function|String|Array*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: builds an array by repeatedly applying a unary function N times  +			//	with a seed value Z. +			o = o || d.global; f = df.lambda(f); +			var t = new Array(n); +			t[0] = z; +			for(var i = 1; i < n; t[i] = z = f.call(o, z), ++i); +			return t;	// Array +		}, +		until: function(/*Function|String|Array*/ pr, /*Function|String|Array*/ f, /*Object*/ z, /*Object?*/ o){ +			// summary: builds an array by repeatedly applying a unary function with  +			//	a seed value Z until the predicate is satisfied. +			o = o || d.global; f = df.lambda(f); pr = df.lambda(pr); +			var t = []; +			for(; !pr.call(o, z); t.push(z), z = f.call(o, z)); +			return t;	// Array +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/functional/zip.js b/includes/js/dojox/lang/functional/zip.js new file mode 100644 index 0000000..523f400 --- /dev/null +++ b/includes/js/dojox/lang/functional/zip.js @@ -0,0 +1,45 @@ +if(!dojo._hasResource["dojox.lang.functional.zip"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.functional.zip"] = true; +dojo.provide("dojox.lang.functional.zip"); + +// This module adds high-level functions and related constructs: +//	- zip combiners + +// Defined methods: +//	- operate on dense arrays + +(function(){ +	var df = dojox.lang.functional; + +	dojo.mixin(df, { +		// combiners +		zip: function(){ +			// summary: returns an array of arrays, where the i-th array  +			//	contains the i-th element from each of the argument arrays. +			// description: This is the venerable zip combiner (for example, +			//	see Python documentation for general details). The returned +			//	array is truncated to match the length of the shortest input +			//	array. +			var n = arguments[0].length, m = arguments.length, i; +			for(i = 1; i < m; n = Math.min(n, arguments[i++].length)); +			var t = new Array(n), j; +			for(i = 0; i < n; ++i){ +				var p = new Array(m); +				for(j = 0; j < m; p[j] = arguments[j][i], ++j); +				t[i] = p; +			} +			return t;	// Array +		}, +		unzip: function(/*Array*/ a){ +			// summary: similar to dojox.lang.functional.zip(), but takes  +			//	a single array of arrays as the input. +			// description: This function is similar to dojox.lang.functional.zip()  +			//	and can be used to unzip objects packed by  +			//	dojox.lang.functional.zip(). It is here mostly to provide  +			//	a short-cut for the different method signature. +			return df.zip.apply(null, a);	// Array +		} +	}); +})(); + +} diff --git a/includes/js/dojox/lang/tests/array.js b/includes/js/dojox/lang/tests/array.js new file mode 100644 index 0000000..292210c --- /dev/null +++ b/includes/js/dojox/lang/tests/array.js @@ -0,0 +1,84 @@ +if(!dojo._hasResource["dojox.lang.tests.array"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.array"] = true; +dojo.provide("dojox.lang.tests.array"); + +dojo.require("dojox.lang.functional"); +dojo.require("dojox.lang.functional.fold"); +dojo.require("dojox.lang.functional.reversed"); + +(function(){ +	var df = dojox.lang.functional, v, isOdd = "%2"; +	 +	var revArrayIter = function(array){ +		this.array    = array; +		this.position = array.length - 1; +	}; +	dojo.extend(revArrayIter, { +		hasNext:	df.lambda("this.position >= 0"), +		next:		df.lambda("this.array[this.position--]") +	}); +	 +	tests.register("dojox.lang.tests.array", [ +		function testFilter1(t){ t.assertEqual(df.filter([1, 2, 3], isOdd), [1, 3]); }, +		function testFilter2(t){ t.assertEqual(df.filter([1, 2, 3], "%2==0"), [2]); }, +		function testFilterIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.filter(iter, isOdd), [3, 1]); +		}, +		function testFilterRev(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.filter(iter, isOdd), df.filterRev([1, 2, 3], isOdd)); +		}, +		 +		function testForEach(t){ +			t.assertEqual((v = [], df.forEach([1, 2, 3], function(x){ v.push(x); }), v), [1, 2, 3]); +		}, +		function testForEachIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual((v = [], df.forEach(iter, function(x){ v.push(x); }), v), [3, 2, 1]); +		}, +		function testForEachRev(t){ +			t.assertEqual((v = [], df.forEachRev([1, 2, 3], function(x){ v.push(x); }), v), [3, 2, 1]); +		}, +		 +		function testMap(t){ t.assertEqual(df.map([1, 2, 3], "+3"), [4, 5, 6]); }, +		function testMapIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.map(iter, "+3"), [6, 5, 4]); +		}, +		function testMapRev(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.map(iter, "+3"), df.mapRev([1, 2, 3], "+3")); +		}, +		 +		function testEvery1(t){ t.assertFalse(df.every([1, 2, 3], isOdd)); }, +		function testEvery2(t){ t.assertTrue(df.every([1, 3, 5], isOdd)); }, +		function testEveryIter(t){ +			var iter = new revArrayIter([1, 3, 5]); +			t.assertTrue(df.every(iter, isOdd)); +		}, +		function testEveryRev1(t){ t.assertFalse(df.everyRev([1, 2, 3], isOdd)); }, +		function testEveryRev2(t){ t.assertTrue(df.everyRev([1, 3, 5], isOdd)); }, + +		function testSome1(t){ t.assertFalse(df.some([2, 4, 6], isOdd)); }, +		function testSome2(t){ t.assertTrue(df.some([1, 2, 3], isOdd)); }, +		function testSomeIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertTrue(df.some(iter, isOdd)); +		}, +		function testSomeRev1(t){ t.assertFalse(df.someRev([2, 4, 6], isOdd)); }, +		function testSomeRev2(t){ t.assertTrue(df.someRev([1, 2, 3], isOdd)); }, + +		function testReduce1(t){ t.assertEqual(df.reduce([4, 2, 1], "x-y"), 1); }, +		function testReduce2(t){ t.assertEqual(df.reduce([4, 2, 1], "x-y", 8), 1); }, +		function testReduceIter(t){ +			var iter = new revArrayIter([1, 2, 4]); +			t.assertEqual(df.reduce(iter, "x-y"), 1); +		}, +		 +		function testReduceRight1(t){ t.assertEqual(df.reduceRight([4, 2, 1], "x-y"), -5); }, +		function testReduceRight2(t){ t.assertEqual(df.reduceRight([4, 2, 1], "x-y", 8), 1); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/curry.js b/includes/js/dojox/lang/tests/curry.js new file mode 100644 index 0000000..cb6fa6a --- /dev/null +++ b/includes/js/dojox/lang/tests/curry.js @@ -0,0 +1,31 @@ +if(!dojo._hasResource["dojox.lang.tests.curry"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.curry"] = true; +dojo.provide("dojox.lang.tests.curry"); + +dojo.require("dojox.lang.functional.curry"); + +(function(){ +	var df = dojox.lang.functional, add5 = df.curry("+")(5), sub3 = df.curry("_-3"), fun = df.lambda("100*a + 10*b + c"); +	tests.register("dojox.lang.tests.curry", [ +		function testCurry1(t){ t.assertEqual(df.curry("+")(1, 2), 3); }, +		function testCurry2(t){ t.assertEqual(df.curry("+")(1)(2), 3); }, +		function testCurry3(t){ t.assertEqual(df.curry("+")(1, 2, 3), 3); }, +		function testCurry4(t){ t.assertEqual(add5(1), 6); }, +		function testCurry5(t){ t.assertEqual(add5(3), 8); }, +		function testCurry6(t){ t.assertEqual(add5(5), 10); }, +		function testCurry7(t){ t.assertEqual(sub3(1), -2); }, +		function testCurry8(t){ t.assertEqual(sub3(3), 0); }, +		function testCurry9(t){ t.assertEqual(sub3(5), 2); }, +		 +		function testPartial1(t){ t.assertEqual(df.partial(fun, 1, 2, 3)(), 123); }, +		function testPartial2(t){ t.assertEqual(df.partial(fun, 1, 2, df.arg)(3), 123); }, +		function testPartial3(t){ t.assertEqual(df.partial(fun, 1, df.arg, 3)(2), 123); }, +		function testPartial4(t){ t.assertEqual(df.partial(fun, 1, df.arg, df.arg)(2, 3), 123); }, +		function testPartial5(t){ t.assertEqual(df.partial(fun, df.arg, 2, 3)(1), 123); }, +		function testPartial6(t){ t.assertEqual(df.partial(fun, df.arg, 2, df.arg)(1, 3), 123); }, +		function testPartial7(t){ t.assertEqual(df.partial(fun, df.arg, df.arg, 3)(1, 2), 123); }, +		function testPartial8(t){ t.assertEqual(df.partial(fun, df.arg, df.arg, df.arg)(1, 2, 3), 123); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/fold.js b/includes/js/dojox/lang/tests/fold.js new file mode 100644 index 0000000..e766c62 --- /dev/null +++ b/includes/js/dojox/lang/tests/fold.js @@ -0,0 +1,64 @@ +if(!dojo._hasResource["dojox.lang.tests.fold"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.fold"] = true; +dojo.provide("dojox.lang.tests.fold"); + +dojo.require("dojox.lang.functional.fold"); +dojo.require("dojox.lang.functional.scan"); +dojo.require("dojox.lang.functional.curry"); + +(function(){ +	var df = dojox.lang.functional, a = df.arg; + +	var revArrayIter = function(array){ +		this.array    = array; +		this.position = array.length - 1; +	}; +	dojo.extend(revArrayIter, { +		hasNext:	df.lambda("this.position >= 0"), +		next:		df.lambda("this.array[this.position--]") +	}); + +	tests.register("dojox.lang.tests.fold", [ +		function testFoldl1(t){ t.assertEqual(df.foldl([1, 2, 3], "+", 0), 6); }, +		function testFoldl2(t){ t.assertEqual(df.foldl1([1, 2, 3], "*"), 6); }, +		function testFoldl3(t){ t.assertEqual(df.foldl1([1, 2, 3], "/"), 1/6); }, +		function testFoldl4(t){ t.assertEqual(df.foldl1([1, 2, 3], df.partial(Math.max, a, a)), 3); }, +		function testFoldl5(t){ t.assertEqual(df.foldl1([1, 2, 3], df.partial(Math.min, a, a)), 1); }, +		 +		function testFoldlIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.foldl(iter, "+", 0), 6); +		}, +		function testFoldl1Iter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.foldl1(iter, "/"), 3/2); +		}, +		 +		function testFoldr1(t){ t.assertEqual(df.foldr([1, 2, 3], "+", 0), 6); }, +		function testFoldr2(t){ t.assertEqual(df.foldr1([1, 2, 3], "*"), 6); }, +		function testFoldr3(t){ t.assertEqual(df.foldr1([1, 2, 3], "/"), 3/2); }, +		function testFoldr4(t){ t.assertEqual(df.foldr1([1, 2, 3], df.partial(Math.max, a, a)), 3); }, +		function testFoldr5(t){ t.assertEqual(df.foldr1([1, 2, 3], df.partial(Math.min, a, a)), 1); }, +		 +		function testScanl1(t){ t.assertEqual(df.scanl([1, 2, 3], "+", 0), [0, 1, 3, 6]); }, +		function testScanl2(t){ t.assertEqual(df.scanl1([1, 2, 3], "*"), [1, 2, 6]); }, +		function testScanl3(t){ t.assertEqual(df.scanl1([1, 2, 3], df.partial(Math.max, a, a)), [1, 2, 3]); }, +		function testScanl4(t){ t.assertEqual(df.scanl1([1, 2, 3], df.partial(Math.min, a, a)), [1, 1, 1]); }, + +		function testScanlIter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.scanl(iter, "+", 0), [0, 3, 5, 6]); +		}, +		function testScanl1Iter(t){ +			var iter = new revArrayIter([1, 2, 3]); +			t.assertEqual(df.scanl1(iter, "*"), [3, 6, 6]); +		}, +		 +		function testScanr1(t){ t.assertEqual(df.scanr([1, 2, 3], "+", 0), [6, 5, 3, 0]); }, +		function testScanr2(t){ t.assertEqual(df.scanr1([1, 2, 3], "*"), [6, 6, 3]); }, +		function testScanr3(t){ t.assertEqual(df.scanr1([1, 2, 3], df.partial(Math.max, a, a)), [3, 3, 3]); }, +		function testScanr4(t){ t.assertEqual(df.scanr1([1, 2, 3], df.partial(Math.min, a, a)), [1, 2, 3]); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/fun_perf.html b/includes/js/dojox/lang/tests/fun_perf.html new file mode 100644 index 0000000..9d19a60 --- /dev/null +++ b/includes/js/dojox/lang/tests/fun_perf.html @@ -0,0 +1,176 @@ +<html> +	<head> +		<title>clocking fun</title> +		<style type="text/css"> +			@import "../../../dojo/resources/dojo.css"; +		</style> +		<script type="text/javascript" src="../../../dojo/dojo.js" djConfig="isDebug:true"></script> +		<script type="text/javascript" src="../functional.js"></script> +		<script type="text/javascript" src="../functional/sequence.js"></script> +		<script type="text/javascript" src="../functional/fold.js"></script> +		<script type="text/javascript"> +			dojo.addOnLoad(function(){ +				var LEN = 2000, ITER = 200, b, e, tests = {}, +					df = dojox.lang.functional, +					sample = df.repeat(LEN, "+1", 0), +					add = df.lambda("+"), +					isOdd = df.lambda("%2"); +					 +				var clock = function(body){ +					var b = new Date(); +					body(); +					var e = new Date(); +					return e.getTime() - b.getTime();	// in ms +				}; +				 +				var log = function(name, body){ +					b = new Date(); +					var ms = clock(body); +					e = new Date(); +					console.log(name + ":", ms); +				}; + +				// filter +				tests["raw filter"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						var t = []; +						for(var j = 0; j < sample.length; ++j){ +							if(isOdd(sample[j])){ t.push(sample[j]); } +						} +					} +				}; +				tests["dojo.filter"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						dojo.filter(sample, isOdd); +					} +				}; +				tests["df.filter"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						df.filter(sample, isOdd); +					} +				}; +				if(sample.filter){ +					tests["Array.prototype.filter"] = function(){ +						for(var i = 0; i < ITER; ++i){ +							sample.filter(isOdd); +						} +					}; +				} + +				// map +				tests["raw map"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						var t = []; +						for(var j = 0; j < sample.length; ++j){ +							t.push(isOdd(sample[j])); +						} +					} +				}; +				tests["dojo.map"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						dojo.map(sample, isOdd); +					} +				}; +				tests["df.map"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						df.map(sample, isOdd); +					} +				}; +				if(sample.map){ +					tests["Array.prototype.map"] = function(){ +						for(var i = 0; i < ITER; ++i){ +							sample.map(isOdd); +						} +					}; +				} + +				// forEach +				tests["raw forEach"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						for(var j = 0; j < sample.length; ++j){ +							isOdd(sample[j]); +						} +					} +				}; +				tests["dojo.forEach"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						dojo.forEach(sample, isOdd); +					} +				}; +				tests["df.forEach"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						df.forEach(sample, isOdd); +					} +				}; +				if(sample.forEach){ +					tests["Array.prototype.forEach"] = function(){ +						for(var i = 0; i < ITER; ++i){ +							sample.forEach(isOdd); +						} +					}; +				} + +				// reduce +				tests["raw reduce"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						var z = 0; +						for(var j = 0; j < sample.length; ++j){ +							z = add(z, sample[j]); +						} +					} +				}; +				tests["df.reduce"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						df.reduce(sample, add, 0); +					} +				}; +				if(sample.reduce){ +					tests["Array.prototype.reduce"] = function(){ +						for(var i = 0; i < ITER; ++i){ +							sample.reduce(add, 0); +						} +					}; +				} + +				// reduceRight +				tests["raw reduceRight"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						var z = 0; +						for(var j = sample.length - 1; j >= 0; --j){ +							z = add(z, sample[j]); +						} +					} +				}; +				tests["df.reduceRight"] = function(){ +					for(var i = 0; i < ITER; ++i){ +						df.reduceRight(sample, add, 0); +					} +				}; +				if(sample.reduceRight){ +					tests["Array.prototype.reduceRight"] = function(){ +						for(var i = 0; i < ITER; ++i){ +							sample.reduceRight(add, 0); +						} +					}; +				} +				 +				var keys = df.keys(tests), i = 0; +				 +				var doTest = function(){ +					log(keys[i], tests[keys[i]]); +					++i; +					if(i < keys.length){ +						setTimeout(doTest, 1); +					}else{ +						console.log("that's all"); +					} +				}; +				 +				setTimeout(doTest, 1); +			}); +		</script> +	</head> +	<body> +		<p>This test is meant to run with Firebug.</p> +	</body> +</html> diff --git a/includes/js/dojox/lang/tests/lambda.js b/includes/js/dojox/lang/tests/lambda.js new file mode 100644 index 0000000..7e5e7ed --- /dev/null +++ b/includes/js/dojox/lang/tests/lambda.js @@ -0,0 +1,24 @@ +if(!dojo._hasResource["dojox.lang.tests.lambda"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.lambda"] = true; +dojo.provide("dojox.lang.tests.lambda"); + +dojo.require("dojox.lang.functional"); +dojo.require("dojox.lang.functional.sequence"); + +(function(){ +	var df = dojox.lang.functional; +	tests.register("dojox.lang.tests.lambda", [ +		function testLambda1(t){ t.assertEqual(df.repeat(3, "3*", 1), [1, 3, 9]); }, +		function testLambda2(t){ t.assertEqual(df.repeat(3, "*3", 1), [1, 3, 9]); }, +		function testLambda3(t){ t.assertEqual(df.repeat(3, "_*3", 1), [1, 3, 9]); }, +		function testLambda4(t){ t.assertEqual(df.repeat(3, "3*_", 1), [1, 3, 9]); }, +		function testLambda5(t){ t.assertEqual(df.repeat(3, "n->n*3", 1), [1, 3, 9]); }, +		function testLambda6(t){ t.assertEqual(df.repeat(3, "n*3", 1), [1, 3, 9]); }, +		function testLambda7(t){ t.assertEqual(df.repeat(3, "3*m", 1), [1, 3, 9]); }, +		function testLambda8(t){ t.assertEqual(df.repeat(3, "->1", 1), [1, 1, 1]); }, +		function testLambda9(t){ t.assertEqual(df.repeat(3, function(n){ return n * 3; }, 1), [1, 3, 9]); }, +		function testLambda10(t){ t.assertEqual(df.repeat(3, ["_-1", ["*3"]], 1), [1, 2, 5]); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/listcomp.js b/includes/js/dojox/lang/tests/listcomp.js new file mode 100644 index 0000000..45cd8ab --- /dev/null +++ b/includes/js/dojox/lang/tests/listcomp.js @@ -0,0 +1,28 @@ +if(!dojo._hasResource["dojox.lang.tests.listcomp"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.listcomp"] = true; +dojo.provide("dojox.lang.tests.listcomp"); + +dojo.require("dojox.lang.functional.listcomp"); +dojo.require("dojox.lang.functional.sequence"); + +(function(){ +	var df = dojox.lang.functional; +	tests.register("dojox.lang.tests.listcomp", [ +		function testIterator1(t){ t.assertEqual(df.repeat(3, function(n){ return n + 1; }, 0), [0, 1, 2]); }, +		function testIterator2(t){ t.assertEqual(df.repeat(3, function(n){ return n * 3; }, 1), [1, 3, 9]); }, +		function testIterator3(t){ t.assertEqual(df.until(function(n){ return n > 10; }, function(n){ return n * 3; }, 1), [1, 3, 9]); }, +		 +		function testListcomp1(t){ t.assertEqual(df.listcomp("i for(var i=0; i<3; ++i)"), [0, 1, 2]); }, +		function testListcomp2(t){ t.assertEqual(df.listcomp("i*j for(var i=0; i<3; ++i) for(var j=0; j<3; ++j)"), [0, 0, 0, 0, 1, 2, 0, 2, 4]); }, +		function testListcomp3(t){ t.assertEqual(df.listcomp("i*j for(var i=0; i<3; ++i) if(i%2==1) for(var j=0; j<3; ++j)"), [0, 1, 2]); }, +		function testListcomp4(t){ t.assertEqual(df.listcomp("i+j for(var i=0; i<3; ++i) for(var j=0; j<3; ++j)"), [0, 1, 2, 1, 2, 3, 2, 3, 4]); }, +		function testListcomp5(t){ t.assertEqual(df.listcomp("i+j for(var i=0; i<3; ++i) if(i%2==1) for(var j=0; j<3; ++j)"), [1, 2, 3]); }, +		function testListcomp6(t){ t.assertEqual(df.listcomp("i for(i=0; i<3; ++i)"), [0, 1, 2]); }, +		function testListcomp7(t){ t.assertEqual(df.listcomp("i*j for(i=0; i<3; ++i) for(j=0; j<3; ++j)"), [0, 0, 0, 0, 1, 2, 0, 2, 4]); }, +		function testListcomp8(t){ t.assertEqual(df.listcomp("i*j for(i=0; i<3; ++i) if(i%2==1) for(j=0; j<3; ++j)"), [0, 1, 2]); }, +		function testListcomp9(t){ t.assertEqual(df.listcomp("i+j for(i=0; i<3; ++i) for(j=0; j<3; ++j)"), [0, 1, 2, 1, 2, 3, 2, 3, 4]); }, +		function testListcomp10(t){ t.assertEqual(df.listcomp("i+j for(i=0; i<3; ++i) if(i%2==1) for(j=0; j<3; ++j)"), [1, 2, 3]); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/main.js b/includes/js/dojox/lang/tests/main.js new file mode 100644 index 0000000..1f0d7ab --- /dev/null +++ b/includes/js/dojox/lang/tests/main.js @@ -0,0 +1,17 @@ +if(!dojo._hasResource["dojox.lang.tests.main"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.main"] = true; +dojo.provide("dojox.lang.tests.main"); + +try{ +	// functional block +	dojo.require("dojox.lang.tests.listcomp"); +	dojo.require("dojox.lang.tests.lambda"); +	dojo.require("dojox.lang.tests.fold"); +	dojo.require("dojox.lang.tests.curry"); +	dojo.require("dojox.lang.tests.misc"); +	dojo.require("dojox.lang.tests.array"); +}catch(e){ +	doh.debug(e); +} + +} diff --git a/includes/js/dojox/lang/tests/misc.js b/includes/js/dojox/lang/tests/misc.js new file mode 100644 index 0000000..f17ea8c --- /dev/null +++ b/includes/js/dojox/lang/tests/misc.js @@ -0,0 +1,31 @@ +if(!dojo._hasResource["dojox.lang.tests.misc"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.tests.misc"] = true; +dojo.provide("dojox.lang.tests.misc"); + +dojo.require("dojox.lang.functional.object"); +dojo.require("dojox.lang.functional.zip"); + +(function(){ +	var df = dojox.lang.functional, fun = df.lambda("100*a + 10*b + c"), result = []; +	df.forIn({a: 1, b: 2}, function(v, i){ result.push("[" + i + "] = " + v); }); +	 +	tests.register("dojox.lang.tests.misc", [ +		function testZip1(t){ t.assertEqual(df.zip([1, 2, 3], [4, 5, 6]), [[1, 4], [2, 5], [3, 6]]); }, +		function testZip2(t){ t.assertEqual(df.zip([1, 2], [3, 4], [5, 6]), [[1, 3, 5], [2, 4, 6]]); }, +		 +		function testUnzip1(t){ t.assertEqual(df.unzip([[1, 4], [2, 5], [3, 6]]), [[1, 2, 3], [4, 5, 6]]); }, +		function testUnzip2(t){ t.assertEqual(df.unzip([[1, 3, 5], [2, 4, 6]]), [[1, 2], [3, 4], [5, 6]]); }, +		 +		function testMixer(t){ t.assertEqual(df.mixer(fun, [1, 2, 0])(3, 1, 2), 123); }, +		function testFlip(t){ t.assertEqual(df.flip(fun)(3, 2, 1), 123); }, +		 +		function testCompose1(t){ t.assertEqual(df.lambda(["+5", "*3"])(8), 8 * 3 + 5); }, +		function testCompose2(t){ t.assertEqual(df.lambda(["+5", "*3"].reverse())(8), (8 + 5) * 3); }, +		 +		function testForIn(t){ t.assertEqual(result.sort().join(", "), "[a] = 1, [b] = 2"); }, +		function testKeys(t){ t.assertEqual(df.keys({a: 1, b: 2, c: 3}), ["a", "b", "c"]); }, +		function testValues(t){ t.assertEqual(df.values({a: 1, b: 2, c: 3}), [1, 2, 3]); } +	]); +})(); + +} diff --git a/includes/js/dojox/lang/tests/runTests.html b/includes/js/dojox/lang/tests/runTests.html new file mode 100644 index 0000000..32fdfdb --- /dev/null +++ b/includes/js/dojox/lang/tests/runTests.html @@ -0,0 +1,9 @@ +<html>
 +	<head>
 +		<title>DojoX Functional Unit Test Runner</title>
 +	    <meta http-equiv="REFRESH" content="0;url=../../../util/doh/runner.html?testModule=dojox.lang.tests.main" /> +	</head>
 +	<body>
 +		<p>Redirecting to D.O.H runner.</p>	
 +	</body>
 +</html> diff --git a/includes/js/dojox/lang/utils.js b/includes/js/dojox/lang/utils.js new file mode 100644 index 0000000..b7926c6 --- /dev/null +++ b/includes/js/dojox/lang/utils.js @@ -0,0 +1,54 @@ +if(!dojo._hasResource["dojox.lang.utils"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code. +dojo._hasResource["dojox.lang.utils"] = true; +dojo.provide("dojox.lang.utils"); + +(function(){ +	var empty = {}, du = dojox.lang.utils; +	 +	dojo.mixin(dojox.lang.utils, { +		coerceType: function(target, source){ +			switch(typeof target){ +				case "number":	return Number(eval("(" + source + ")")); +				case "string":	return String(source); +				case "boolean":	return Boolean(eval("(" + source + ")")); +			} +			return eval("(" + source + ")"); +		}, +		 +		updateWithObject: function(target, source, conv){ +			// summary: updates an existing object in place with properties from an "source" object. +			// target: Object: the "target" object to be updated +			// source: Object: the "source" object, whose properties will be used to source the existed object. +			// conv: Boolean?: force conversion to the original type +			if(!source){ return target; } +			for(var x in target){ +				if(x in source && !(x in empty)){ +					var t = target[x]; +					if(t && typeof t == "object"){ +						du.updateObject(t, source[x]); +					}else{ +						target[x] = conv ? du.coerceType(t, source[x]) : dojo.clone(source[x]); +					} +				} +			} +			return target;	// Object +		}, +	 +		updateWithPattern: function(target, source, pattern, conv){ +			// summary: updates an existing object in place with properties from an "source" object. +			// target: Object: the "target" object to be updated +			// source: Object: the "source" object, whose properties will be used to source the existed object. +			// pattern: Array: an array of properties to be copied +			// conv: Boolean?: force conversion to the original type +			if(!source || !pattern){ return target; } +			for(var x in pattern){ +				if(x in source && !(x in empty)){ +					target[x] = conv ? du.coerceType(pattern[x], source[x]) : dojo.clone(source[x]); +				} +			} +			return target;	// Object +		} +	}); +})(); + +}  | 
