Unexpected behavior from list of texts

This a part of a hint system I’m working on. The important part for this example is that you can ask for a hint with HINT [TOPIC], and get a list of all past responses for a topic with RECALL HINT [TOPIC]. My problem starts with storing the past responses in the Carry out asking for hints about rule. The if statement to guard against adding duplicate responses doesn’t work, and when I list the responses later on, they are all identical (as you will see from running the test me.)

I know I’m misunderstanding something fundamental about Inform text. Can anyone help me out?

Lab is a room. The garden is north of the lab.
	
A hint topic is a kind of thing.
A hint topic has number called the hint level. The hint level is usually 0. 
A hint topic can be listed or unlisted. A hint topic is usually listed.
A hint topic can be progressive or non-progressive. A hint topic is usually non-progressive.
A hint topic has a list of texts called the progression. The progression of a hint topic is usually {}.
A hint topic has a text called the last hint. The last hint of a hint topic is usually "".
A hint topic has a list of texts called the history. The history of a hint topic is usually {}.

asking for hints about is an action out of world applying to one thing. Understand "hint [any hint topic]" as asking for hints about. 

recalling hints about is an action out of world applying to one thing. Understand "recall hint [any hint topic]" as recalling hints about.

Check recalling hints about:
	if the number of entries in the history of the noun is 0:
		say "You haven't seen any hints for that." instead;

Carry out recalling hints about:	
	say "You've seen the following hints about [the noun]:[line break]";
	repeat with item running through the history of the noun:
		say "[item][line break]";

hinting is an object based rulebook producing texts. The hinting rules have default success.

hinting rules have outcomes go on (no outcome).

activating is an object based rulebook. The activating rules have outcomes activate (success) and deactivate (failure). The activating rules have default no outcome.

Activating a hint topic (called HT):
	activate;								

Carry out asking for hints about:
	follow the activating rules for the noun;
	if the rule succeeded:
		let current hint be the text produced by the hinting rules for the noun;
		if the rule succeeded:
			say "[current hint][line break]";				
			now the last hint of the noun is current hint;
			if current hint is not listed in the history of the noun:
				add current hint to the history of the noun;
		otherwise:
			say "There is no hint for that right now.";
	otherwise:
		say "There is no hint for that right now.";

hinting:
    rule fails;

hinting a progressive hint topic (called HT):
	if the hint level of HT is less than the number of entries in the progression of HT:
		let result be the substituted form of "[entry (hint level of HT + 1) in the progression of the HT]";
		increment the hint level of HT;
		rule succeeds with result result;
	otherwise:
		rule succeeds with result the substituted form of "[entry (number of entries in the progression of HT) in the progression of HT]";
		 
the cat is a progressive hint topic. The progression is {"hint 1", "hint 2", "hint 3"}.

resetting is an action out of world. Understand "reset" as resetting.
Carry out resetting:
	now the hint level of the cat is 0;
	
the dog is a hint topic.

hinting the dog:
	rule succeeds with result "dog hint";

test me with "hint cat/hint cat/recall hint cat/hint dog/hint dog/recall hint dog".
1 Like

This is the output I see when compiling that in 10.1:

Welcome
An Interactive Fiction
Release 1 / Serial number 240412 / Inform 7 v10.1.2 / D
 
Lab
 
>test me
(Testing.)
 
>[1] hint cat
hint 1
 
>[2] hint cat
hint 2
 
>[3] recall hint cat
You've seen the following hints about the cat:
hint 1
hint 2
 
>[4] hint dog
dog hint
 
>[5] hint dog
dog hint
 
>[6] recall hint dog
You've seen the following hints about the dog:
dog hint
 
>

It looks like what I thought you were describing. Is this the same output you’re seeing? and, if so, what’s wrong with it?

1 Like

Hmm. I was running it in 6M62. Maybe I’ve run into a bug/strange behavior that’s been fixed in 10?

(EDIT: What I was seeing was that hint 2 was repeated for cat, and dog hint was repeated for dog.)

I wonder if I can upgrade my current project (2+ years old, in 9.3) to 10.1 easily. That would fix the problem.

Thanks for trying out the code.

1 Like

It works in 6M62 if you remove:

The progression of a hint topic is usually {}.
The history of a hint topic is usually {}.
1 Like

Ah. Fantastic. I was just looking at those sentences and wondering if they were necessary. I never suspected they were harmful. Thanks!

1 Like

I haven’t dug into this, but I suspect that Inform was making the progression of every hint topic be the same (shared) list of texts. Similarly for history.

2 Likes

Pretty close – same shared list of values, not texts. Probably a side effect of the compiler taking an empty list literal ({}) to be a list of generic values instead of the type specified by the list declaration, which has come up before for 6M62 and I think is a fixed bug.

The relevant generated I6:

Array LIST_CONST_16014 --> (85721088) LIST_OF_TY MAX_POSITIVE_NUMBER VALUE_TY 0 ;	! <--- VALUE_TY is incorrect

Array BC_86 --> LIST_CONST_16014 0;
Array BC_291 --> LIST_CONST_16014 0;
Array BC_300 --> LIST_CONST_16014 0;

Class K18_hint_topic 
	class K2_thing
	...
	with p18_history BC_86
	...
;

Object I153_cat ""
	class K18_hint_topic
	with name 'cat' 'hint//p' 'topics//p' 
	...
	with p18_history BC_291
	...
;

Object I154_dog ""
	class K18_hint_topic
	with name 'dog' 'hint//p' 'topics//p' 
	...
	with p18_history BC_300
	...
;