![](/img/trans.png)
[英]The addEventListener does not work in external Javascript file, but does when placed directly on ASP page. Why?
[英]I keep everything in an external .js file. But not all functions are used on every page. Does this affect speed?
我的应用程序的JavaScript / jQuery包含在一个外部scripts.js
文件中。 通常看起来像这样:
$('document').on('ready', function() {
giraffe();
elephant();
zebra();
});
function giraffe() {
// code
}
function elephant() {
// code
}
function zebra() {
// code
}
giraffe()
仅用于/animal/giraffe
可用的视图
elephant()
仅用于/animal/elephant
可用的视图
zebra()
仅用于/animal/zebra
的视图,
但是所有这3个都应该在可用的/animal/all
视图上运行。 这是一个简单的示例,但这是将它们全部保存在一个.js
文件中的原因,除了将HTTP请求保持在最低限度之外。
我的问题是,这会影响JavaScript渲染吗? 即使未在/animal/zebra
上使用giraffe()
(没有要处理的元素),仍在调用它。 如果JS / jQuery没有任何作用,它会忽略该函数吗? 我确定已读取整个脚本,这可能需要时间。 那么,处理此问题的最佳方法是什么?
为了避免冲突,我在js文件的顶部创建了条件语句,以仅运行活动页面所需的功能:
$('document').on('ready', function() {
var body = $('body');
if( body.hasClass('giraffe') ) {
giraffe();
}
if( body.hasClass('elephant') ) {
elephant();
}
if( body.hasClass('zebra') ) {
zebra();
}
});
这比我想要的更为冗长,但是可以成功地使这些功能保持模块化/无冲突。 我欢迎对此解决方案进行改进。
当然,只运行所需的代码会更好。 这并不困难; 唯一的次要复杂性是处理/animals/all
情况。 如果要将所有代码保存在一个文件中,可以采用以下方式:
var animals = {
giraffe: function() {
console.log( "I'm a giraffe" );
},
elephant: function() {
console.log( "I'm an elephant" );
},
zebra: function() {
console.log( "I'm a zebra" );
}
};
$(function() {
var animal = location.pathname.split('/').pop();
if( animal == 'all' ) {
for( var animal in animals ) {
animals[animal]();
}
}
else if( animal in animals ) {
animals[animal]();
}
else {
console.log( "I'm a mystery animal" );
}
});
您实际上可以通过在Stack Overflow上转到如下所示的URL来测试该代码,然后将该代码粘贴到JavaScript控制台中:
https://stackoverflow.com/animal/giraffe
https://stackoverflow.com/animal/elephant
https://stackoverflow.com/animal/zebra
https://stackoverflow.com/animal/ocelot
https://stackoverflow.com/animal/all
更新:好的,因此您在评论中解释了实际情况要复杂一些。 如果对任何人都有用,我将在此处保留此代码,但是对于您的情况,您可能更接近于已经拥有的代码所需要的内容。
WRT的问题是,当您在与页面无关的页面上使用哪种动物功能时,当然取决于它的编码方式。 它可能无法成功执行任何操作,或者可能有错误,对吧?
由于我们在谈论jQuery代码,因此这里有两个示例。 假设您有按ID查找元素的代码,然后假定该元素存在:
var zebraElement = $('#zebra')[0];
console.log( zebraElement.value );
在#zebra
元素存在的页面上,此代码将记录其value
属性。 (我为讨论起见,它是一个具有值的元素,例如输入元素。)
但是,如果#zebra
不存在,那么zebraElement
是undefined
,并且attemping访问其value
在调试器将失败和土地。
OTOH,如果您这样编码:
var $zebra = $('#zebra');
console.log( $zebra.val() );
如果缺少#zebra
,它不会失败,它将成功打印undefined
而不会引起错误。
类似地,如果您有使用$().each()
,则当缺少元素时,它将通常不会失败地运行,因为它根本不会执行回调函数:
$('.animal').each( function( i, e ) {
console.log( $(e).val() );
});
如果没有元素带有class="animal"
,则将永远不会到达console.log()
调用。 因此没有错误,它什么也不做。
根据您的操作,这可能是一种完全合理的方法,它仅触发您需要的行为—只需确保您的代码通过不做任何事情即可处理丢失的DOM元素。
另外,请务必阅读nick的答案以获得更多见解。
还有一个更新…在注释中,您提到了在body
元素上键入类名。 做到这一点的一种好方法类似于上面的代码示例。 您不需要为每个动物设置条件,只需一个循环和一个条件即可:
var animals = {
giraffe: function() {
console.log( "I'm a giraffe" );
},
elephant: function() {
console.log( "I'm an elephant" );
},
zebra: function() {
console.log( "I'm a zebra" );
}
};
$(function() {
var $body = $('body');
for( var animal in animals ) {
if( $body.hasClass(animal) ) {
animals[animal]();
}
}
});
因此,例如,如果您具有<body class="giraffe zebra">
,它将调用animals.giraffe()
和animals.zebra()
函数。
实际上,这里有两个问题,一个是是否加载所有功能,另一个是是否运行所有功能。 Michael Geary在其他答案中已经很好地解决了有关是否全部运行它们(以及仅运行所需功能的一些解决方案)的问题。
那么,您应该全部加载它们吗? 您需要权衡下载更大文件所需的时间,而不是提出额外的http请求。 只有3个“组”的功能在3个页面之间共享(并且一个页面使用所有这些功能),并且当您希望用户定期更改页面时,我会使用一个文件。
一旦项目变得很大,您将需要使用requirejs之类的工具来管理脚本并异步加载它们。 异步加载js脚本会提高页面的速度(以及页面的感知速度),如果出现问题(尤其是第三方托管的脚本),您的页面将无法获得帮助。 您当然可以在没有库的情况下执行此操作:
使用HTML5:
<script async src="http://google.com/script.js"></script>
有上百万种使用纯JS异步加载的方式,一种方式是:
<script>
var resource = document.createElement('script');
resource.src = "//google.com/script.js";
var script = document.getElementsByTagName('script')[0];
script.parentNode.insertBefore(resource, script);
</script>
Javascript将忽略任何未“调用”的函数。 就是 如果您没有在/ elephant或/ all页面以外的任何页面上都不调用Elephant(),则它将永远不会使用,也不会给您带来任何错误。
但是,您可能不希望在不用于快速加载页面的页面上不显示功能。 考虑为某些页面分离JS文件,或者通过从诸如PHP之类的后端服务器加载某些JS脚本来确定需要哪些功能。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.