Well, if you look back through this thread, you’ll see that Inform isn’t inherently slow. Inform games can be fast or slow, depending on what they do. The problem is it’s hard to know what’s slow unless you’re a serious I6 maven. Most game designers pick some tools from the manual, get the effect they want, and don’t worry about efficiency. That’s what they should be doing, but unfortunately the platform isn’t as forgiving as it should be.
The games run on a virtual machine, and the interpreters aren’t as aggressively optimized as big-label VMs like Javascript. That’s one thing. Then the interpreter might be built on top of Javascript, or on top of a low-power mobile CPU. That’s another thing. Result: an N^2 loop over 1000 objects is undesirable.
At the low level, I6 generates efficient byte code, because I6 is a low-level language and is easy to compile. (Again, it doesn’t have giant compiler teams working on optimizing it, so it does miss tricks. But hand-crafting efficient I6 is straightforward.)
At the next level up, I7’s libraries – which are hand-crafted I6 – are a bit of a mix. Some of that code is tight; some could use some work.
The I6 code that I7 generates, from user code, is fairly good. It’s also a minority of the problem; i.e., it’s generally a thin layer that calls down to the library level. (Of course, if you write nested “repeat through everything” loops, I7 will generate nested repeat-through-everything loops, and then it’s not so thin.)
But at this point there are enough layers that the whole system has some slack in it. A simple-appearing construct like “try taking the foo” invokes a complex action mechanism, which invokes a complex scope mechanism, which checks a lot of objects, and each object check is a property read, and the property read does some type-checking… so low-level code gets invoked a whole lot.
The good news is that this problem is amenable to improvements at every level. We talk about optimizing low-level functions, because they invoked thousands of times. We also talk about ways for scope-checking to cache its results. And about ways for rulebook invocations to be compiled down to more efficient code. And, since all of that is hard work, we wind up going back to the author and saying “Could you not check scope so many times per turn? I know it’s hard to see where it’s happening. But it’s kind of important.”