在Dart中动态加载类

时间:2013-02-05 10:04:27

标签: dart dart-mirrors

所以,我调查镜子,他们可能是一个选择,但鉴于他们的异性,他们可能真的很难使用或从长远来看不可行。由于它们目前不受支持(只是一种游戏),所以它们目前还不是真的可行。

问题:给出一系列字符串,例如。 [ "Foo", "Bar" ]中的基类ApplicationWidget以及library corelib;中每个字符串FooWidgetBarWidget的相应类},目前最优雅的方法是让library applibrary;将字符串转换为相应类的实例,适用于dart2js

为清晰起见,等效的PHP伪示例,

Application

输出

<?php # example

namespace corelib;

class Widget {
    function name() { 
        return \get_called_class(); 
    }
}

class Application {
    static function resolve($name, $library) { 
        $class = $library.'\\'.$name.'Widget'; 
        return new $class;
    }
}

namespace applibrary;

class FooWidget extends \corelib\Widget {
    // ...
}

class BarWidget extends \corelib\Widget {
    // ...
}

$foowidget = \corelib\Application::resolve('Foo', 'applibrary');
$barwidget = \corelib\Application::resolve('Bar', 'applibrary');

echo "{$foowidget->name()} <br> {$barwidget->name()}";

1 个答案:

答案 0 :(得分:1)

如果您可以验证字符串列表,那么目前最好的方法(直到dart2js中的镜像支持变得更好),可能是if语句。

// toy implementation
Widget getWidget(name) {
  switch (name) {
     case "Foo": return new FooWidget();
     case "Bar": return new FooWidget();
     default: // handle error
  } 
} 

// elsewhere:
var fooWidget = getWidget("Foo");
var barWidget = getWidget("Bar");

xyzWidget类列表将是一个有限列表(因为您无法在运行时动态链接代码)。

当然,更优雅的实现是使用镜像(如下所示,供参考,尽管它目前不符合dar2js标准)

Future<Widget> getWidget(library, name) {
  var completer = new Completer<Widget>();
  MirrorSystem ms = currentMirrorSystem();
  ClassMirror cm = ms.libraries[library].classes[name];
  // instantiate an instance of the class
  cm.newInstance(null,[]).then((instance) => completer.complete(instance));

  return completer.future;
}

// elsewhere:   
getWidget("applibrary","FooWidget").then((Widget widget) {
  // do something with widget
});