Performance 写得少,表现好,可能吗?
在过去的几天里,我一直在想一种方法,以避免需要编写大量代码,同时保持我正在开发的Air桌面游戏的良好性能,作为一种爱好 游戏是一种垂直射击游戏,由多个实体移动和检查碰撞组成。有很多不同类型的单元。每一帧我都有类似的内容:Performance 写得少,表现好,可能吗?,performance,actionscript-3,loops,design-patterns,Performance,Actionscript 3,Loops,Design Patterns,在过去的几天里,我一直在想一种方法,以避免需要编写大量代码,同时保持我正在开发的Air桌面游戏的良好性能,作为一种爱好 游戏是一种垂直射击游戏,由多个实体移动和检查碰撞组成。有很多不同类型的单元。每一帧我都有类似的内容: entity.execute(); public var foo:Function; 更简单的方法是让所有不同的实体继承实体类,并手动自定义它们。这是缓慢而繁琐的,并且很难维护。但它速度快,性能好 另一种方法是只有一个实体类,只需使用某种组合来简单地添加“行为”。例如,我有
entity.execute();
public var foo:Function;
更简单的方法是让所有不同的实体继承实体类,并手动自定义它们。这是缓慢而繁琐的,并且很难维护。但它速度快,性能好
另一种方法是只有一个实体类,只需使用某种组合来简单地添加“行为”。例如,我有一个master类,里面有各种各样的动作、攻击等,不同的实体使用它们
这种方法的问题是,调用一个函数很慢,根据我的测试,它比只调用代码(在execute()内)慢3倍
我进退两难,我找不到一种方法来重用代码块来装饰通用实体实例,并保持良好的性能。看来我得用一个或另一个
我试着使用[Inline],但我读到它不是一个稳定的特性,我没有看到任何明显的性能改进,尽管我没有对它进行太多测试
任何见解都值得赞赏。通过继承进行抽象是一种很好的面向对象模式,我认为它维护起来并不缓慢或繁琐。关注点的分离将使继承基本实体类的类更加清晰;同时,减少复制的代码。接口将进一步抽象具体类型 ActionScript不支持像C#这样的语言所具有的强大的面向对象语言功能-没有抽象基类,没有分部类,有限的模板/泛型,有限的多态性。组合和装饰器模式可能会强制使用动态类,这也会由于类型检查而降低运行时的速度 也许更大的问题是实体类中的业务逻辑太多。我想一些世界容器或控制器将负责碰撞检测 你可以考虑的是像Box 2D这样的物理引擎。p>
有BXX2D的端口,由CouthBig(以前的炼金术,FlasCC)构建,它是AVM2的C++编译器,能够通过精益优化的字节码快速闪存到10X,字节码具有高性能的Flash访问代码(称为域存储器)。 这就是游戏的制作方式
看看Jesse Sternberg的《如果使用AS3物理引擎听起来有趣的话》在游戏开发中,有一些常用的加速flash的方法。其中之一是避免使用显示对象,而使用简单的位图。在这种情况下,您将一个阶段作为位图,并将所有游戏状态保留在轻量级对象中,然后定期(在输入帧或计时器上)将游戏状态快照绘制到该阶段位图数据中(使用
copyPixels
)
示意图:假设你有一个单位游戏
class PseudoSprite {
public var x:uint;
public var y:uint;
public var currentAnimFrame:uint;
protected var snapshotCreator:AbstractSnapshotCreator;
public function makeSnapshot():BitmapData {
return snapshotCreator.createSnapshot(currentAnimFrame);
}
....
}
class Unit extends PseudoSprite {
public var directionAngle:Number = 0;
public var speed:uint = 0;
function Unit() {
snapshotCreator = UnitSnapshotCreator.instance;
}
public function doStep():void {
x = //count x by speed and direction
y = //count y by speed and direction
animationFrame++;
}
}
class Game {
public var stage:Bitmap;
private var objects:Vector.<PseudoSprite> = new <PseudoSprite>[
new Unit(), new Unit()];
public function step() {
for each (var unit:PseudoSprite in objects) {
unit.doStep();
//draw unit.snapshot() to the stage bitmap data
}
}
}
类伪精灵{
公共变量x:uint;
公共变量:uint;
公共框架:uint;
受保护的var snapshotCreator:AbstractSnapshotCreator;
公共函数makeSnapshot():位图数据{
返回snapshotCreator.createSnapshot(currentAnimFrame);
}
....
}
类单位扩展伪精灵{
公共var方向角:数字=0;
公共无功转速:uint=0;
功能单元(){
snapshotCreator=UnitSnapshotCreator.instance;
}
公共函数doStep():void{
x=//按速度和方向计算x
y=//按速度和方向计算y
animationFrame++;
}
}
班级游戏{
公共var阶段:位图;
私有变量对象:Vector.=new[
新单位(),新单位();
公共职能步骤(){
对于每个(变量单位:对象中的伪精灵){
单位:doStep();
//将unit.snapshot()绘制到后台位图数据
}
}
}
因此,您可以看到:您可以使用普通OOP构建整个单元(或所有游戏对象)层次结构,并获得一些合适的性能 经过一些测试后,我发现我可以做如下事情:
entity.execute();
public var foo:Function;
然后,当我创建实体时,我可以:
entity.foo = myCustomFoo;
然后在主循环中,我可以:
entity.foo();
这与在实体实例中调用本机成员函数一样有效。警告,不要创建访问函数的getter,它会变得慢得多 首先,你的问题对StackOverflow来说太宽泛了。另外,我不知道为什么不使用继承或接口?对于使用一个
实体
类,您是否尝试在本地定义对所需方法的引用,并查看这是否会影响速度?它确实很广泛,但它与编程架构有着内在的联系。如果你有足够的经验,你以前可能遇到过这种情况,因此能够提供帮助。关于您的问题,它们表明您没有阅读我的问题。投票被否决,因为该问题意味着性能的关键在于代码。代码和代码执行只是性能难题的一部分,所以这个问题是无关的,没有真正的答案。好吧,性能的关键在于代码。谢谢你的输入,但我使用的是Starling。有趣的是,我不需要在这个游戏中使用Box2D,我很少使用非物理。只有一些反弹计算之类的东西,我可以自己写。你知道,如果你能提供一个理由,为什么你对答案投反对票,那就太好了。虽然我没有给你投反对票,但我可以说这个答案并没有提供太多有用的信息。你可以展示速度测试的数据和结果,是什么让你相信这是最好的方法,而不仅仅是说速度更快。我不记得了