JavaScript根据函数名字符串调用函数的方法

最近遇到一个问题,JavaScript如何通过函数名的字符串来调用这个函数,到stackoverflow上逛了圈,收获良多,这里总结下:

如果你是要直接调用全局的函数,可以用如下方式:

//定义一个名为foo的函数
function foo() 
{
    alert(1);
}
//第一种调用方式
window['foo']();
//第二种调用方式
eval('foo()');

如果你想要在一个对象里面调用对象自己的属性函数,可以用如下方式:

var test = {
	foo : function(a) {
		alert(a);
	},
	bar : function() {
		var property = 'foo';
		var parameter = ['this is a test!'];
		var fn = this[property];
		if(typeof fn === 'function') {
			fn.apply(this, parameter);
		}
	}
};
test.bar();

上面这段代码是我写的一个小例子,其中的

fn.apply(this, parameter);

有几个好处,第一点就是可以让你调用的foo这个属性函数能够使用到当前的this,如果不用apply是无法调用到当前的this的。第二点就是传递参数变得很自由,如果属性函数需要传入多个参数可以用数组传入。

上面这段小代码就是我在“基于Requirejs和Backbonejs,将Zend Framework 2官方Demo改为RESTful架构的应用”里面做到自动路由分发的核心代码。

使用原生JavaScript模拟getElementByClassName

最近在工作中,由于有一个插件必须使用jquery-pack.js,而这个包又是非常古老的jquery,所以又的函数是无法使用的,例如$()选择器以及parent()都取不到标签的内容,所以没办法,只能用原生的JavaScript了,为了实现这个功能,我得通过HTML标签的Class来获得标签的DOM结构。在JavaScript 内建的核心中,document对象及element对象总共可以通过三个方式来获取其下的元素,分别是:getElementById(‘id’) 、getElementsByName(‘name’) 、getElementsByTagName(‘tag’)  。可是在设计网页时,最常常需要使用到的class却没有相对应的方法可以去获取className相同的元素。不过我们可以自己写一个,代码以很简单:

function getElementByClassName(tagName, className)
{
	var tag = document.getElementsByTagName(tagName);
	var tagAll = [];
	for (var i = 0; i < tag.length; i++) {
		if (tag[i].className.indexOf(className) != -1) {
			tagAll[tagAll.length] = tag[i];
		}
	}
	return tagAll;
}

原理就是通过获取指定的标签,使用getElementsByTagName来获取标签的内容,然后根据标签的className跟传进来的参数进行对比,如果相等就放入数组中最后返回。

浅谈C++与PHP中的构造函数与析构函数

        第一次接触构造函数和析构函数,是学C++的时候,然而一年多没接触C++,似乎对于这两个“类中函数”,早已忘得差不多了。这几天在学PHP,又遇到了这两函数,由于对于构造函数和析构函数的了解不深,今天就好好研究了一下下。

      先说说在C++中的构造函数和析构函数。C++中提供了构造函数来处理对象的初始化,但是不能说构造函数的主要作用是用来对对象进行初始化。构造函数是一种特殊的成员函数,不需要用户调用,在建立对象时,构造函数就会自动执行。而且构造函数的名字必须与类名相同。注意,不能由用户任意命名。有时候也会在想,我们都是在什么时候调用构造函数的?其实,在类对象进入其作用域是就调用了构造函数。构造函数没有返回值,所以也不需要在定义构造函数时声明函数类型,这是构造函数和一般函数的一个不同之处。在定义构造函数的时候,可以带参数,也可以不带参数。但是呢,带参数的构造函数有一个很大的优点:采用带参数的构造函数,在调用不同对象的构造函数时,可以将不同的数据从外面传递给构造函数,以实现不同的初始化。不过这时候要注意几点。首先,我们已经知道用户是不能调用构造函数的,所以不能像常规的调用函数的方法来对构造函数给出实参。在C++中,构造函数的实参是在定义对象时给出的。

        不过这时候我们也会在想,如果用户没有定义构造函数,那会有构造函数么?其实,如果用户没有自己定义构造函数,则C++系统会自动生成一个构造函数。在了解构造函数的时候,我们还得知道一个名词:重载。构造函数的重载,通俗来说就是定义很多个不同的构造函数,但是,函数名必须相同,其中不相同的是,构造函数的参数的个数和参数的类型不同。还需明白的一点是:构造函数的参数的值既可以通过实参传递,也可指定为某些默认值。不过,一般不应同时使用构造函数的重载还有默认参数的构造函数。

        析构函数是什么?我们可以这样理解,析构函数是与构造函数作用相反的函数。从析构函数的名字也可以看出。数学中,数A的相反数是-A。所以可以映射到C++中,构造函数A的作用相反的函数就是析构函数~A。注意,不是-A!就像我们不能说构造函数的主要作用是用来对对象进行初始化一样,析构函数的作用并不是删除对象,而是在撤销对象占用的内存之前完成一些清理工作。同构造函数一样,析构函数没有返回值,没有函数类型。不过析构函数也没有函数参数。可以说析构函数是“三无函数”。因为没有函数参数,所以析构函数不能被重载。因此只有一个析构函数!要切记。在使用构造函数和析构函数时,其顺序可以简单记为:先构造的后析构,后构造的先析构。就好比栈操作,先进后出。

        简单了解完C++中的构造函数和析构函数后,现在来说说PHP中的构造函数与析构函数。在PHP4中,构造函数是类中的一个特殊函数,构造函数与类同名。当使用 new 操作符创建一个类的实例时,构造函数将会自动调用。如果一个类没有构造函数,则调用基类的构造函数,前提是基类有构造函数。然而,在PHP5引入了一个声明构建函数的标准方法: __construct()。这里需要提醒的是:construct()函数前的下划线“_”是两个!!!如果少写一个“_”,结果就错了。见Example1

 Example1:

 Code:

<?php 

	/*类的实例4:实现Iterator接口的迭代  */
		class MyIterator implements Iterator
		{
			private $var = array();
			public function _constuct($array)
			{
				if(is_array($array))
				{
					$this-&gt;var = $array;
				}
			}

			public function rewind()
			{
				echo "rewinding\n";
				reset($this-&gt;var);
			}

			public function current()
			{
				$var = current($this-&gt;var);
				echo "current:$var\n";
				return $var;
			}

			public function key()
			{
				$var = key($this-&gt;var);
				echo "key:$var\n";
				return $var;
			}

			public function next()
			{
				$var = next($this-&gt;var);
				echo "next:$var\n";
				return $var;
			}

			public function valid()
			{
				$var = $this-&gt;current() !== false;
				echo "valid:{$var}\n";
				return $var;
			}
		}

		$values = array(1,2,3);
		$it = new MyIterator($values);

		foreach ($it as $a =&gt; $b)
		{
			print "$a:$b\n";
		}

输出结果: 

 

 

Example2:

Code:

<?php 
	/*类的实例4:实现Iterator接口的迭代  */
		class MyIterator implements Iterator
		{
			private $var = array();
			public function __constuct($array)
			{
				if(is_array($array))
				{
					$this-&gt;var = $array;
				}
			}

			public function rewind()
			{
				echo "rewinding\n";
				reset($this-&gt;var);
			}

			public function current()
			{
				$var = current($this-&gt;var);
				echo "current:$var\n";
				return $var;
			}

			public function key()
			{
				$var = key($this-&gt;var);
				echo "key:$var\n";
				return $var;
			}

			public function next()
			{
				$var = next($this-&gt;var);
				echo "next:$var\n";
				return $var;
			}

			public function valid()
			{
				$var = $this-&gt;current() !== false;
				echo "valid:{$var}\n";
				return $var;
			}
		}

		$values = array(1,2,3);
		$it = new MyIterator($values);

		foreach ($it as $a =&gt; $b)
		{
			print "$a:$b\n";
		}

输出结果:

 

但是,如果没有定义构造函数__construct()怎么办?此时,系统会自动查找是否有与类同名的函数,如果有,此时,构造函数将会变成与类同名的函数。如Example2。

如果同时存在__construct()函数和与类同名的函数,如example3,此时,两个函数是一样的,只执行一个函数。

Example3:

Code: 

<?php 

	/*类的实例4:实现Iterator接口的迭代  */
		class MyIterator implements Iterator
		{
			private $var = array();
			public function __construct($array)
			{
				if(is_array($array))
				{
					$this-&gt;var = $array;
				}
			}

			public function MyIterator($array)
			{
				if(is_array($array))
				{
					$this-&gt;var = $array;
				}
			} 

			public function rewind()
			{
				echo "rewinding\n";
				reset($this-&gt;var);
			}

			public function current()
			{
				$var = current($this-&gt;var);
				echo "current:$var\n";
				return $var;
			}

			public function key()
			{
				$var = key($this-&gt;var);
				echo "key:$var\n";
				return $var;
			}

			public function next()
			{
				$var = next($this-&gt;var);
				echo "next:$var\n";
				return $var;
			}

			public function valid()
			{
				$var = $this-&gt;current() !== false;
				echo "valid:{$var}\n";
				return $var;
			}
		}

		$values = array(1,2,3);
		$it = new MyIterator($values);

		foreach ($it as $a =&gt; $b)
		{
			print "$a:$b\n";
		}

输出结果:

        对于析构函数,在PHP4中,析构函数是不存在的。但是,PHP5中有析构函数。其他的与C++中的一样。记得析构函数是没有参数的。

使用Javascript获得日期

Javascript获取日期可以使用Date对象。如果构造函数不带参数,其默认是获取当前日期。

var myDate=new Date();

Date 对象方法

FF: Firefox, IE: Internet Explorer

方法 描述
Date() 返回当日的日期和时间。
getDate() 从 Date 对象返回一个月中的某一天 (1 ~ 31)。
getDay() 从 Date 对象返回一周中的某一天 (0 ~ 6)。
getMonth() 从 Date 对象返回月份 (0 ~ 11)。
getFullYear() 从 Date 对象以四位数字返回年份。
getYear() 请使用 getFullYear() 方法代替。
getHours() 返回 Date 对象的小时 (0 ~ 23)。
getMinutes() 返回 Date 对象的分钟 (0 ~ 59)。
getSeconds() 返回 Date 对象的秒数 (0 ~ 59)。
getMilliseconds() 返回 Date 对象的毫秒(0 ~ 999)。
getTime() 返回 1970 年 1 月 1 日至今的毫秒数。
getTimezoneOffset() 返回本地时间与格林威治标准时间 (GMT) 的分钟差。
getUTCDate() 根据世界时从 Date 对象返回月中的一天 (1 ~ 31)。
getUTCDay() 根据世界时从 Date 对象返回周中的一天 (0 ~ 6)。
getUTCMonth() 根据世界时从 Date 对象返回月份 (0 ~ 11)。
getUTCFullYear() 根据世界时从 Date 对象返回四位数的年份。
getUTCHours() 根据世界时返回 Date 对象的小时 (0 ~ 23)。
getUTCMinutes() 根据世界时返回 Date 对象的分钟 (0 ~ 59)。
getUTCSeconds() 根据世界时返回 Date 对象的秒钟 (0 ~ 59)。
getUTCMilliseconds() 根据世界时返回 Date 对象的毫秒(0 ~ 999)。
parse() 返回1970年1月1日午夜到指定日期(字符串)的毫秒数。
setDate() 设置 Date 对象中月的某一天 (1 ~ 31)。
setMonth() 设置 Date 对象中月份 (0 ~ 11)。
setFullYear() 设置 Date 对象中的年份(四位数字)。
setYear() 请使用 setFullYear() 方法代替。
setHours() 设置 Date 对象中的小时 (0 ~ 23)。
setMinutes() 设置 Date 对象中的分钟 (0 ~ 59)。
setSeconds() 设置 Date 对象中的秒钟 (0 ~ 59)。
setMilliseconds() 设置 Date 对象中的毫秒 (0 ~ 999)。
setTime() 以毫秒设置 Date 对象。
setUTCDate() 根据世界时设置 Date 对象中月份的一天 (1 ~ 31)。
setUTCMonth() 根据世界时设置 Date 对象中的月份 (0 ~ 11)。
setUTCFullYear() 根据世界时设置 Date 对象中的年份(四位数字)。
setUTCHours() 根据世界时设置 Date 对象中的小时 (0 ~ 23)。
setUTCMinutes() 根据世界时设置 Date 对象中的分钟 (0 ~ 59)。
setUTCSeconds() 根据世界时设置 Date 对象中的秒钟 (0 ~ 59)。
setUTCMilliseconds() 根据世界时设置 Date 对象中的毫秒 (0 ~ 999)。
toSource() 返回该对象的源代码。
toString() 把 Date 对象转换为字符串。
toTimeString() 把 Date 对象的时间部分转换为字符串。
toDateString() 把 Date 对象的日期部分转换为字符串。
toGMTString() 请使用 toUTCString() 方法代替。
toUTCString() 根据世界时,把 Date 对象转换为字符串。
toLocaleString() 根据本地时间格式,把 Date 对象转换为字符串。
toLocaleTimeString() 根据本地时间格式,把 Date 对象的时间部分转换为字符串。
toLocaleDateString() 根据本地时间格式,把 Date 对象的日期部分转换为字符串。
UTC() 根据世界时返回 1970 年 1 月 1 日 到指定日期的毫秒数。
valueOf() 返回 Date 对象的原始值。

参考文献:http://1.sunchunman.sinaapp.com/?p=192

Tonitech版权所有 | 转载请注明出处: http://www.tonitech.com/?p=128