据我所知,CommonJS和AMD之间的区别仅仅在于CommonJS需要制作一个静态包,以便在运行时可以解析所有依赖关系,而AMD允许我们以异步方式加载/解析deps。几乎所有我读过的内容都解释了这种方式的主要区别,但我正在阅读Addy Osmani的“编写模块化JavaScript”,我对一些AMD示例提出了一些问题:
// A module_id (myModule) is used here for demonstration purposes only
define('myModule',
['foo', 'bar'],
// module definition function
// dependencies (foo and bar) are mapped to function parameters
function ( foo, bar ) {
// return a value that defines the module export
// (i.e the functionality we want to expose for consumption)
// create your module here
var myModule = {
doStuff:function(){
console.log('Yay! Stuff');
}
}
return myModule;
});
// An alternative example could be..
define('myModule',
['math', 'graph'],
function ( math, graph ) {
// Note that this is a slightly different pattern
// With AMD, it's possible to define modules in a few
// different ways due as it's relatively flexible with
// certain aspects of the syntax
return {
plot: function(x, y){
return graph.drawPie(math.randomGrid(x,y));
}
}
};
});
现在,当我读到这篇文章时,我认为这与CommonJS不同,因为我们将一个回调函数传递给define函数,以便在加载/解析我们的依赖项时调用我们的回调函数。这样,只有当我们需要的东西都可用时才能异步调用我们的回调......很酷......然后我看了下面的例子:
// Consider 'foo' and 'bar' are two external modules
// In this example, the 'exports' from the two modules loaded are passed as
// function arguments to the callback (foo and bar)
// so that they can similarly be accessed
require(['foo', 'bar'], function ( foo, bar ) {
// rest of your code here
foo.doSomething();
});
define(function ( require ) {
var isReady = false, foobar;
// note the inline require within our module definition
require(['foo', 'bar'], function (foo, bar) {
isReady = true;
foobar = foo() + bar();
});
// we can still return a module
return {
isReady: isReady,
foobar: foobar
};
});
现在看完这两个例子后我很困惑。似乎说require()
用于动态加载的依赖项,但这不是我们首先使用AMD / define的原因吗?支持异步/动态加载deps ??如果require()
允许我们动态加载deps,那么define()
有什么用处,或者我应该说,那么AMD的define()
与普通的CJS实现有什么不同?