From a0039bdd9ac50d7a1462de8c837f2c94658a1e19 Mon Sep 17 00:00:00 2001 From: Ketmar Dark Date: Sat, 19 Mar 2016 08:39:21 +0200 Subject: [PATCH] much faster and better searching for actordef by classtype:classname --- d2dadefs.d | 218 +++++++++++++++++++++++++++++++------------------------------ dengapi.d | 14 ++-- 2 files changed, 118 insertions(+), 114 deletions(-) diff --git a/d2dadefs.d b/d2dadefs.d index aab9afd..911ea5c 100644 --- a/d2dadefs.d +++ b/d2dadefs.d @@ -40,91 +40,90 @@ public enum { AF_NOANIMATE = BIT!(6), // don't do animation } + // ////////////////////////////////////////////////////////////////////////// // // known D2D actors (and pseudoactors) struct ActorDefD2D { - string classtype; - string classname; - string fullname; + StrId classtype; + StrId classname; ushort mapid; // thing id in map - this (string ctype, string cname, ushort thid) { classtype = ctype; classname = cname; fullname = classtype~":"~classname; mapid = thid; } + this (string ctype, string cname, ushort thid) { + classtype = StrPool.intern(ctype); + classname = StrPool.intern(cname); + mapid = thid; + } string toString () const { import std.string : format; - return "ActorDefD2D(%s, %s, %s)".format(classtype/*.quote*/, classname/*.quote*/, mapid); + return "ActorDefD2D(%s, %s, %s)".format(classtype.get, classname.get, mapid); } } -immutable ActorDefD2D[$] d2dactordefs = [ - ActorDefD2D("playerstart", "Player1", 1), - ActorDefD2D("playerstart", "Player2", 2), - ActorDefD2D("playerstart", "DMStart", 3), - ActorDefD2D("item", "Clip", 100), - ActorDefD2D("item", "Shell", 101), - ActorDefD2D("item", "Rocket", 102), - ActorDefD2D("item", "Cell", 103), - ActorDefD2D("item", "Ammo", 104), - ActorDefD2D("item", "ShellBox", 105), - ActorDefD2D("item", "RocketBox", 106), - ActorDefD2D("item", "CellPack", 107), - ActorDefD2D("item", "StimPack", 108), - ActorDefD2D("item", "MediKit", 109), - ActorDefD2D("item", "BackPack", 110), - ActorDefD2D("item", "Chainsaw", 111), - ActorDefD2D("item", "Shotgun", 112), - ActorDefD2D("item", "SuperShotgun", 113), - ActorDefD2D("item", "MachineGun", 114), - ActorDefD2D("item", "RocketLauncher", 115), - ActorDefD2D("item", "Plasmagun", 116), - ActorDefD2D("item", "BFG900", 117), - ActorDefD2D("item", "ArmorGreen", 118), - ActorDefD2D("item", "ArmorBlue", 119), - ActorDefD2D("item", "MegaSphere", 120), - ActorDefD2D("item", "Invulnerability", 121), - ActorDefD2D("item", "Aqualung", 122), - ActorDefD2D("item", "KeyRed", 123), - ActorDefD2D("item", "KeyGreen", 124), - ActorDefD2D("item", "KeyBlue", 125), - ActorDefD2D("item", "ProtectionSuit", 126), - ActorDefD2D("item", "Super", 127), - ActorDefD2D("item", "TorchRed", 128), - ActorDefD2D("item", "TorchGreen", 129), - ActorDefD2D("item", "TorchBlue", 130), - ActorDefD2D("item", "Gor1", 131), - ActorDefD2D("item", "FCan", 132), - ActorDefD2D("item", "Gun2", 133), - ActorDefD2D("monster", "Demon", 200), - ActorDefD2D("monster", "Imp", 201), - ActorDefD2D("monster", "Zombie", 202), - ActorDefD2D("monster", "Sergeant", 203), - ActorDefD2D("monster", "Cyberdemon", 204), - ActorDefD2D("monster", "Chaingunner", 205), - ActorDefD2D("monster", "BaronOfHell", 206), - ActorDefD2D("monster", "HellKnight", 207), - ActorDefD2D("monster", "Cacodemon", 208), - ActorDefD2D("monster", "LostSoul", 209), - ActorDefD2D("monster", "PainElemental", 210), - ActorDefD2D("monster", "SpiderMastermind", 211), - ActorDefD2D("monster", "Arachnotron", 212), - ActorDefD2D("monster", "Mancubus", 213), - ActorDefD2D("monster", "Revenant", 214), - ActorDefD2D("monster", "Archvile", 215), - ActorDefD2D("monster", "Fish", 216), - ActorDefD2D("monster", "Barrel", 217), - ActorDefD2D("monster", "Robot", 218), - ActorDefD2D("monster", "Man", 219), -]; - - -public immutable ActorDefD2D[ushort] d2dactordefsById; -//immutable ActorDefD2D[string] d2dactordefsByTN; // by "type:name" +immutable ActorDefD2D[] d2dactordefs; +public immutable ActorDefD2D[ushort] d2dactordefsById; // by mapid shared static this () { - foreach (const ref ActorDefD2D d2da; d2dactordefs) { - d2dactordefsById[d2da.mapid] = d2da; - //d2dactordefsByTN[d2da.fullname] = d2da; - } + d2dactordefs = [ + ActorDefD2D("playerstart", "Player1", 1), + ActorDefD2D("playerstart", "Player2", 2), + ActorDefD2D("playerstart", "DMStart", 3), + ActorDefD2D("item", "Clip", 100), + ActorDefD2D("item", "Shell", 101), + ActorDefD2D("item", "Rocket", 102), + ActorDefD2D("item", "Cell", 103), + ActorDefD2D("item", "Ammo", 104), + ActorDefD2D("item", "ShellBox", 105), + ActorDefD2D("item", "RocketBox", 106), + ActorDefD2D("item", "CellPack", 107), + ActorDefD2D("item", "StimPack", 108), + ActorDefD2D("item", "MediKit", 109), + ActorDefD2D("item", "BackPack", 110), + ActorDefD2D("item", "Chainsaw", 111), + ActorDefD2D("item", "Shotgun", 112), + ActorDefD2D("item", "SuperShotgun", 113), + ActorDefD2D("item", "MachineGun", 114), + ActorDefD2D("item", "RocketLauncher", 115), + ActorDefD2D("item", "Plasmagun", 116), + ActorDefD2D("item", "BFG900", 117), + ActorDefD2D("item", "ArmorGreen", 118), + ActorDefD2D("item", "ArmorBlue", 119), + ActorDefD2D("item", "MegaSphere", 120), + ActorDefD2D("item", "Invulnerability", 121), + ActorDefD2D("item", "Aqualung", 122), + ActorDefD2D("item", "KeyRed", 123), + ActorDefD2D("item", "KeyGreen", 124), + ActorDefD2D("item", "KeyBlue", 125), + ActorDefD2D("item", "ProtectionSuit", 126), + ActorDefD2D("item", "Super", 127), + ActorDefD2D("item", "TorchRed", 128), + ActorDefD2D("item", "TorchGreen", 129), + ActorDefD2D("item", "TorchBlue", 130), + ActorDefD2D("item", "Gor1", 131), + ActorDefD2D("item", "FCan", 132), + ActorDefD2D("item", "Gun2", 133), + ActorDefD2D("monster", "Demon", 200), + ActorDefD2D("monster", "Imp", 201), + ActorDefD2D("monster", "Zombie", 202), + ActorDefD2D("monster", "Sergeant", 203), + ActorDefD2D("monster", "Cyberdemon", 204), + ActorDefD2D("monster", "Chaingunner", 205), + ActorDefD2D("monster", "BaronOfHell", 206), + ActorDefD2D("monster", "HellKnight", 207), + ActorDefD2D("monster", "Cacodemon", 208), + ActorDefD2D("monster", "LostSoul", 209), + ActorDefD2D("monster", "PainElemental", 210), + ActorDefD2D("monster", "SpiderMastermind", 211), + ActorDefD2D("monster", "Arachnotron", 212), + ActorDefD2D("monster", "Mancubus", 213), + ActorDefD2D("monster", "Revenant", 214), + ActorDefD2D("monster", "Archvile", 215), + ActorDefD2D("monster", "Fish", 216), + ActorDefD2D("monster", "Barrel", 217), + ActorDefD2D("monster", "Robot", 218), + ActorDefD2D("monster", "Man", 219), + ]; + foreach (const ref ActorDefD2D d2da; d2dactordefs) d2dactordefsById[d2da.mapid] = d2da; } @@ -138,11 +137,11 @@ public struct ImgSprite { } +// ////////////////////////////////////////////////////////////////////////// // public final class ActorDef { - string classtype; - string classname; - string fullname; - uint id; // actor's unique id + StrId classtype; + StrId classname; + //uint id; // actor's unique id // animation sequences for stated; keyed by state strid StrId[][][uint] anims; // [statestrid][dir][pos] @@ -223,13 +222,15 @@ public final class ActorDef { return null; } - private __gshared uint nextId = 1; + //private __gshared uint nextId = 1; this (string ctype, string cname) { - classtype = ctype; - classname = cname; - fullname = classtype~":"~classname; - id = nextId++; + classtype = StrPool.intern(ctype); + classname = StrPool.intern(cname); + //classtype = ctype; + //classname = cname; + //fullname = classtype~":"~classname; + //id = nextId++; } void clearAllFrames (StrId state) { @@ -279,19 +280,27 @@ public final class ActorDef { if (fiThink is null || !aid.valid) return; fiThink(aid); } -} +static: + // return `true` to stop + bool forEach (bool delegate (ActorDef d) dg) { + foreach (ActorDef adef; actordefs.byValue) if (dg(adef)) return true; + return false; + } -// ////////////////////////////////////////////////////////////////////////// // -public __gshared ActorDef[string] actordefs; // by fullname + void forEach (void delegate (ActorDef d) dg) { + foreach (ActorDef adef; actordefs.byValue) dg(adef); + } +} +// ////////////////////////////////////////////////////////////////////////// // public ActorDef findD2DActorDef (ushort mapid) { if (mapid == 0) assert(0); - if (mapid == 1 || mapid == 2) return findActorDefByFullName("monster:Player"); + if (mapid == 1 || mapid == 2) return findActorDef("monster", "Player"); if (auto dad = mapid in d2dactordefsById) { - auto adef = findActorDefByFullName(dad.fullname); - if (adef is null) throw new Exception("can't find DACS actor definition for D2D actor '"~dad.fullname~"'"); + auto adef = findActorDef(dad.classtype, dad.classname); + if (adef is null) throw new Exception("can't find DACS actor definition for D2D actor '"~dad.classtype.get~":"~dad.classname.get~"'"); return adef; } import std.conv : to; @@ -302,40 +311,37 @@ public ActorDef findD2DActorDef (ushort mapid) { // ////////////////////////////////////////////////////////////////////////// // import dacs.actor; +__gshared ActorDef[ulong] actordefs; // by (name<<32)|type + mixin(Actor.FieldGetMixin!("classtype", StrId)); // fget_classtype mixin(Actor.FieldGetMixin!("classname", StrId)); // fget_classname +ulong ctn2idx (uint ctid, uint cnid) { pragma(inline, true); return ((cast(ulong)cnid)<<32)|ctid; } +ulong ctn2idx (StrId ct, StrId cn) { pragma(inline, true); return ctn2idx(ct.id, cn.id); } + + public ActorDef findActorDef (ActorId aid) { + pragma(inline, true); if (!aid.valid) return null; - //conwriteln("findActorDef(", aid.id, ") '", aid.fget_classtype.get, ":", aid.fget_classname.get, "'"); return findActorDef(aid.fget_classtype, aid.fget_classname); } -public ActorDef findActorDefByFullName (const(char)[] fullname) { - if (auto fd = fullname in actordefs) return *fd; - return null; -} +public ActorDef findActorDef (StrId ctype, StrId cname) { /*pragma(inline, true);*/ return actordefs.get(ctn2idx(ctype.id, cname.id), null); } public ActorDef findActorDef (const(char)[] ctype, const(char)[] cname) { - if (ctype.length+cname.length > 1024) assert(0); - char[1025] buf; - buf[0..ctype.length] = ctype[]; - buf[ctype.length] = ':'; - buf[ctype.length+1..ctype.length+1+cname.length] = cname[]; - if (auto fd = buf[0..ctype.length+1+cname.length] in actordefs) return *fd; - return null; + auto ctid = ctype in StrPool; + auto cnid = cname in StrPool; + if (!ctid || !cnid) return null; + return actordefs.get(ctn2idx(ctid, cnid), null); } -public ActorDef findActorDef (StrId ctype, StrId cname) { return findActorDef(ctype.get, cname.get); } - - public ActorDef registerActorDef (string classtype, string classname) { - string fullname = classtype~":"~classname; - if (fullname !in actordefs) actordefs[fullname] = new ActorDef(classtype, classname); - if (auto fd = fullname in actordefs) return *fd; - assert(0); + auto ct = StrPool.intern(classtype); + auto cn = StrPool.intern(classname); + if (findActorDef(ct, cn) is null) actordefs[ctn2idx(ct, cn)] = new ActorDef(classtype, classname); + return actordefs[ctn2idx(ct, cn)]; } diff --git a/dengapi.d b/dengapi.d index a9123b8..da43eaa 100644 --- a/dengapi.d +++ b/dengapi.d @@ -91,7 +91,7 @@ void updateActorClasses (int iteration) { foreach (string ctype; dacsClassTypes(iteration)) { foreach (auto mod; dacsClassModules(ctype, iteration)) { auto adef = registerActorDef(mod.rmoduletype.classtype, mod.rmoduletype.classname); - conwriteln("found info for actor '", adef.fullname, "'"); + conwriteln("found info for actor '", mod.rmoduletype.classtype, ":", mod.rmoduletype.classname, "'"); { auto animInitFn = FuncPool.findByFQMG(mod.name~".initializeAnim", ":void"); if (animInitFn !is null) adef.setAnimInitFunc(animInitFn); @@ -382,9 +382,7 @@ public void registerAPI () { //dvm = new DACSVM(); // initialize actor animation - foreach (ActorDef adef; actordefs.byValue) { - adef.callAnimInit(); - } + ActorDef.forEach((adef) => adef.callAnimInit()); conwriteln("API registered"); } @@ -471,7 +469,7 @@ public void loadMapMonsters () { auto adef = findD2DActorDef(thing.type); if (adef is null) { if (auto did = thing.type in d2dactordefsById) { - conwriteln("ignoring D2D thing '", did.fullname, "'"); + conwriteln("ignoring D2D thing '", did.classtype.get, ":", did.classname.get, "'"); } else { conwriteln("ignoring unknown D2D thing with mapid ", thing.type); } @@ -502,10 +500,10 @@ public void loadMapMonsters () { if ((aid.flags!uint&AF_NOCOLLISION) == 0) ugActorModify!true(aid); } - foreach (ActorDef adef; actordefs.byValue) { - conwriteln("loading graphics for '", adef.fullname, "'"); + ActorDef.forEach((adef) { + conwriteln("loading graphics for '", adef.classtype.get, ":", adef.classname.get, "'"); adef.loadGraphics(); - } + }); //Actor.dumpActors(); conwriteln("initial snapshot size: ", Actor.snapshotSize, " bytes"); -- 2.11.4.GIT