I’m trying to create a disintegrator box in Inform6 that removes everything inside when you turn it on. To get rid of each and every object put inside the box, I do this:
Object -> DisintegratorBox "disintegrator box"
with name "disintegrator" "box",
before [ i ;
SwitchOn:
objectloop (i in self)
remove i;
"A puff of smoke rises from the box. The things that were inside are no more.";
],
has switchable openable container;
The objectloop aborts with the message “[** Programming error: objectloop broken because the object lighter was moved while the loop passed through it **]”. One object in the box winds up removed and the rest remain. What’s the correct way to implement this? Am I going to have to tinker with the library?
The objectloop construct iterates down a linked list. If you yank the current object out of the list, the iteration gets screwed up. You can’t use objectloop that way.
I guess you could say
prev = nothing;
objectloop (i in self) {
if (prev) remove (prev);
prev = i;
}
if (prev) remove (prev);
That never touches the current object in the iteration, so I think it’ll work. But it’s obfuscatory coding.
EDIT-ADD: Actually, I think Egon’s suggestion will work – although I haven’t compiled a test case. But it will be much slower than my code. That’s because the “(i && i in self)” expression is complex, so the compiler will generate an objectloop that runs through every object instead of just the contents of self.