9

阅读 requireJs 文档,
以修复循环依赖,建议使用exports为模块创建一个空对象,该对象可立即供其他模块引用。

我尝试了这段代码,但它似乎不起作用。怎么了?

PS:
阅读评论以查看输出,
尤其是 setTimeout 调用中的 B 模块。


// A module
define([
    'b'
], function (b) {
    console.log('B:', b); // B, Object
    var A = {
        boo: 1
    };

    return A;
});

// B module
define([
    'a',
    'exports'
], function (a, exports) {
    console.log('A:', a); // A, undefined (as I was expecting)
    exports.A = function () {
        return a;
    }

    var B = {
        bar: 1
    };

    setTimeout(function () {
        console.log('exports.A', exports.A()); // exports.A undefined 
                                           // I would like to access the A object
                                           // which is defined in A module
    }, 500);

    return B;
});

// main.js

(function () {

    define([
        'a'
    ], function () {
    });
}());
4

3 回答 3

1

您应该能够使用require()B 模块中的同步版本来访问“A”模块:

// B module
define([
    'a',
    'exports'
], function (a, exports) {
    console.log('A:', a); // A, undefined (as I was expecting)
    exports.A = function () {
        return require('a');
    }
    ...
});
于 2014-04-24T23:05:29.083 回答
0

一种选择是不返回模块本身,而是实例化模块的函数(在此示例中,它将是 typescript 中定义的构造函数,底部是生成的 js 代码- 请注意,接口不会生成 .js 代码)

  • 文件 IA.ts

    /// <reference path="IB.ts" />
    interface IA{
        funcA();
        _classB : IB;
    }
    
  • 文件 IB.ts

    /// <reference path="IA.ts" />
    interface IB{
        funcB();
        _classA : IA;
    }
    
  • 文件类A.ts

    /// <reference path="IA.ts" />
    /// <reference path="IB.ts" />
    
    export class ClassA implements IA
    {
        _classB : IB = null;
    
        constructor(classB : IB)
        {
            this._classB = classB;
            if (classB){
                this._classB._classA = this;
            }
            return this;
        }
    
        funcA(){
            console.log('I am ClassA');
        }
    }
    
  • 文件类B.ts

    /// <reference path="IA.ts" />
    /// <reference path="IB.ts" />
    export class ClassB implements IB
    {
        _classA : IA = null;
        constructor(classA : IA)
        {
            this._classA = classA;
            if (classA){
                this._classA._classB = this;
            }
            return this;
        }
        funcB(){
            console.log('I am ClassB');
        }
    }
    
  • 文件 MainTest.ts

    /// <reference path="../../def/require.d.ts" />
    /// <reference path="IA.ts" />
    /// <reference path="IB.ts" />
    define(['ClassA', 'ClassB'],
        function (classA, classB)
        {
            var aa : IA = new classA.ClassA();
            var bb : IB = new classB.ClassB(aa);
    
            bb.funcB();
            aa._classB.funcB();
            bb._classA.funcA();
            aa.funcA();
        });
    

以及生成的js代码:

  • 文件 ClassA.js

    define(["require", "exports"], function(require, exports) {
        var ClassA = (function () {
            function ClassA(classB) {
                this._classB = null;
                this._classB = classB;
                if (classB) {
                    this._classB._classA = this;
                }
                return this;
            }
            ClassA.prototype.funcA = function () {
                console.log('I am ClassA');
            };
            return ClassA;
        })();
        exports.ClassA = ClassA;
    });
    
  • 文件 ClassB.js

    define(["require", "exports"], function(require, exports) {
        var ClassB = (function () {
            function ClassB(classA) {
                this._classA = null;
                this._classA = classA;
                if (classA) {
                    this._classA._classB = this;
                }
                return this;
            }
            ClassB.prototype.funcB = function () {
                console.log('I am ClassB');
            };
            return ClassB;
        })();
        exports.ClassB = ClassB;
    });
    
  • 文件 MainTest.js

    define(['ClassA', 'ClassB'], function (classA, classB) {
    
        var aa = new classA.ClassA();
        var bb = new classB.ClassB(aa);
    
        bb.funcB();
        aa._classB.funcB();
        bb._classA.funcA();
        aa.funcA();
    
    });
    

最后,输出将是:

我是B级

我是B级

我是A级

我是A级

于 2014-03-21T16:47:03.797 回答
0

我经常遇到循环问题,使用 AMD 模块构建一个应用程序核心,它既支持许多模块,又包含配置或其他有用的对象供这些模块使用。

我今天做了一些实验,这似乎工作得很好。

define(['exports', 'underscore', './config', './mediator'],
  function (exports, _, Backbone, config, Mediator){

    Core = /* ... */

    // Publicize a core 'singleton' so that it's dependencies can access it, and so can modules that define it as a dependency themselves.
    core = new Core()
    exports.core = core //publicize it in a way that supports circularity
    return core // And also publicize it normally
  }
)

这两个对象都是“===”,所以这看起来很有希望。

编辑:

上述方法在优化后不起作用。这是另一种可能(未经测试)的方法: https ://github.com/requirejs/example-multipage/blob/master/www/js/app/main1.js#L2

define(function (require) {
  var $ = require('jquery'),
      lib = require('./lib'),
      Core;

   Core = /* ... */

   return new Core()
});
于 2013-07-16T00:16:52.630 回答