如何将函数制为空函数且不执行参数?

zkzk12345 2013-03-02 03:49:20
当我们开发时需要输出很多log信息,例如使用下面的函数
log = function(msg)
{ console.log(msg);}

在发布版中我们不希望打印log,因此在发布版将log函数置空如下
log = function(msg){};

但实际上这种方式不能防止参数部分的执行,如调用log(getName()),则其中的getName()无论如何都会被执行。

而我希望完全不执行log函数及其参数部分,需要怎么做呢?各位大牛求指导!
...全文
676 26 打赏 收藏 转发到动态 举报
写回复
用AI写文章
26 条回复
切换为时间正序
请发表友善的回复…
发表回复
ftiger 2013-03-03
  • 打赏
  • 举报
回复
想了半天只能这样

log= function () { 
	if(arguments.length==1 && typeof arguments[0] !="function"){
		console.log(arguments[0]);
		return;
	}
	
	var back;
	if(typeof arguments[0] =="function"){
		console.log(Array.slice(arguments,1));
		back =arguments[0].apply(arguments[0],Array.slice(arguments,1));
	}else if(arguments.length>2 && (typeof arguments[1] =="function")){
		var fn = arguments[1];
		var args= Array.slice(arguments,2);
		back =fn.apply(arguments[0],args);
	}
	console.log(back);
	return back;
}

/*********************************/
function test() {
    console.log("test is run!!");
    return "test";
}
 
function sum(a ,b) {
    console.log("sum is run!!");
    return a+b;
}

var person={
	age:10,
	say:function (str) {
		return str + this.age;
	}
};

log("Test start!");
log(test);
log(sum,10,100);
log(person,person.say,"My age is");

maximelei 2013-03-03
  • 打赏
  • 举报
回复
js加一個全局變量控制可以呀 var flag=true|false (看發怖版本而定) log = function(msg){ if(flag=true){ console.log(msg); } }
zkzk12345 2013-03-03
  • 打赏
  • 举报
回复
引用 18 楼 ftiger 的回复:
sum.log(getNum1.log(), getNum2.log());
好吧确实可以,不过这种写法已经影响到代码可读性了,另外对Function的改动其实只能影响到函数,而不能影响到如a+b这种通用代码段 如sum.log( a+b, c*d)
ftiger 2013-03-03
  • 打赏
  • 举报
回复
好吧,this有问题,纯函数可行,对象的方法有问题。
zkzk12345 2013-03-03
  • 打赏
  • 举报
回复
引用 24 楼 Mackz 的回复:
我觉得你用log函数的方法就有问题,为什么要把其他函数执行结果直接作为参数来调用log函数?这样一者你必须在函数中都返回一个值,而不是所有函数都有这个必要;二者如果你需要使用这个函数的返回值,又怎么做?所以还是规规矩矩在需要的地方把返回值赋予变量,变量作为参数去调用log函数;另外调试日志功能可能也在函数中吧,这样也更现实。否则,要么就是上面出来的丑陋的代码,要么就没法,……
我觉得我有必要解释一下,在两种场合需要去掉log或者说去除掉log对性能影响: 1、对外发布版,需要完全去掉log函数,这点用正则表达式直接删log部分代码是可行的,但是这种写法 var msg = getName(); log(msg); 则会有问题。如果msg纯粹是为打印log准备的数据(没有在其他地方被引用)则应该删除语句以减少消耗,然而这种写法无法用简单的方式检测到这段无用代码并且给予删除。因此我会选择 log(getName()); 这种方式只有一行,这是有利于对外发布版时删除log的。 2、开发中控制log等级,此时没必要用删除的手段,当控制log等级时我会将部分log函数置空或重新定义函数如下: log.info = function(msg){}; log.info = function(msg){console.log(msg);} 二者可以根据情况选择。但这种方式没法完全去掉参数部分的执行消耗,当参数部分是一个函数时【如log(getName())】,尤其这个函数代价较大时,这种消耗就更应该去掉。同理,较长的或者消耗较大的表达式也最好去掉如 log.info("arguments of func TEST: name="+name+" arg1="+arg1+" arg2="+arg2+" result="+result); 可能arg1是某种长字串,那么大量字串的连接也是有性能消耗的 ————这就引发我的问题,如何完全不执行参数部分呢? jswatcher给出的方法可以用于明确知道函数代价较大时使用,而且消耗小(编写时只要额外添加一小段语句,执行时用一个判断语句取代整个参数段的执行,可读性强),勉强可以达到要求。 而ftiger提供的方法不像是个log函数,而是个代码执行器了,需要拆分函数和参数来使用,而且确实无法用于长表达式的情况。也有可能是我表述不清使你误解,这里表示抱歉了。 就此结贴,虽然没有类似C++的方案,毕竟脚本有其自身特点,不过还是很感谢各位!
line_us 2013-03-03
  • 打赏
  • 举报
回复
观摩深入的讨论很有启发
菜牛 2013-03-03
  • 打赏
  • 举报
回复
我觉得你用log函数的方法就有问题,为什么要把其他函数执行结果直接作为参数来调用log函数?这样一者你必须在函数中都返回一个值,而不是所有函数都有这个必要;二者如果你需要使用这个函数的返回值,又怎么做?所以还是规规矩矩在需要的地方把返回值赋予变量,变量作为参数去调用log函数;另外调试日志功能可能也在函数中吧,这样也更现实。否则,要么就是上面出来的丑陋的代码,要么就没法,因为作为参数的函数肯定是先执行的。 var msg = myFun(); log(msg);
ftiger 2013-03-03
  • 打赏
  • 举报
回复
sum.log( a+b, c*d) ================ 这个已经有点钻牛角尖了吧。你代码会log这个? log一般就当监视器用吧。当计算器的场合可以忽略不计了。
ftiger 2013-03-02
  • 打赏
  • 举报
回复
sum.log(getNum1.log(), getNum2.log());
zkzk12345 2013-03-02
  • 打赏
  • 举报
回复
引用 16 楼 ftiger 的回复:
你试过了吗? sum.log(10,100); 在Function.prototype.log 中判断是否继续执行本函数。 但不会影响sum(10,100);
我明白你的意思,但是我要的不是这个, 比如sum.log(getNum1(), getNum2()); 我想要一种方法可以不执行getNum1(), getNum2()这两个函数
ftiger 2013-03-02
  • 打赏
  • 举报
回复
你试过了吗? sum.log(10,100); 在Function.prototype.log 中判断是否继续执行本函数。 但不会影响sum(10,100);
zkzk12345 2013-03-02
  • 打赏
  • 举报
回复
引用 14 楼 ftiger 的回复:
这样就行了 JavaScript code?1234Function.prototype.log= function () { //屏蔽下面语句再试验 //console.log(this.apply(this,arguments));}
你可能误解了我的意思了,我是想要一种方法可以不执行函数及其参数段,即代码 funA(funB());中的funB()不被执行。 而你的代码只是改变了.log函数的功能,并不能达到 test.log(funB());中的“funB()”不执行的效果。~~~
ftiger 2013-03-02
  • 打赏
  • 举报
回复
这样就行了

Function.prototype.log= function () {
		//屏蔽下面语句再试验
		//console.log(this.apply(this,arguments));
}
ftiger 2013-03-02
  • 打赏
  • 举报
回复
如果8楼成立,那么你看看这个


	Function.prototype.log= function () {
		var _self = this;
		//屏蔽下面语句再试验
		console.log(_self.apply(this,arguments));
	}
	

	function test() {
		console.log("test is run!!");
		return "test";
	}

	function sum(a ,b) {
		console.log("sum is run!!");
		return a+b;
	}

	test.log();
	sum.log(10,100);
	console.log(sum(10,100));


zkzk12345 2013-03-02
  • 打赏
  • 举报
回复
引用 8 楼 jswatcher 的回复:
A trick here: Java code?1234567891011var noLog = true; // release version// noLog = false; // development version log( noLog ? null : getName()); //all your log line, should have a f……
赞!再封装一下应该就OK了,就是写起来有点麻烦哈,不过你启发了我,写成以下方式更方便一些 var nolog = true; log( nolog && getName() ) 另外,还是想看看有没有改变log这个函数的方式达到我的目的~~ 如果没有的话就结贴了
jswatcher 2013-03-02
  • 打赏
  • 举报
回复
引用 9 楼 zkzk12345 的回复:
因为实际上某些时候我只是想通过调节debug等级屏蔽一些无用的log,此时我也不希望有额外的性能损耗,毕竟执行log函数+执行参数部分 是有性能损耗的。去掉这些损耗,可以更直观的观察程序性能
看看我8楼的方法是否满足你的要求?
jswatcher 2013-03-02
  • 打赏
  • 举报
回复

// Bug fix for #8, line 11:
//By this trick, when noLog is true, messageExpression will not be executed!
zkzk12345 2013-03-02
  • 打赏
  • 举报
回复
因为实际上某些时候我只是想通过调节debug等级屏蔽一些无用的log,此时我也不希望有额外的性能损耗,毕竟执行log函数+执行参数部分 是有性能损耗的。去掉这些损耗,可以更直观的观察程序性能
jswatcher 2013-03-02
  • 打赏
  • 举报
回复
A trick here:

var noLog = true; // release version
// noLog = false;    // development version

log( noLog ? null : getName());


//all your log line, should have a form:

log ( noLog ? null : messageExpression );

//By this trick, when noLog is false, messageExpression will not be executed!
zkzk12345 2013-03-02
  • 打赏
  • 举报
回复
引用 5 楼 ftiger 的回复:
看错要求不,不如用正则表达式处理过代码再发布,清理所有的log。
发布时删除是比较常用的做法了,继续求其他解法 还是先谢谢热心解答~
加载更多回复(6)

87,991

社区成员

发帖
与我相关
我的任务
社区描述
Web 开发 JavaScript
社区管理员
  • JavaScript
  • 无·法
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧