MCPcopy Create free account
hub / github.com/NetHack/NetHack / losespells

Function losespells

src/spell.c:1762–1827  ·  view source on GitHub ↗

forget a random selection of known spells due to amnesia; they used to be lost entirely, as if never learned, but now we just set the memory retention to zero so that they can't be cast */

Source from the content-addressed store, hash-verified

1760 they used to be lost entirely, as if never learned, but now we
1761 just set the memory retention to zero so that they can't be cast */
1762void
1763losespells(void)
1764{
1765 int n, nzap, i;
1766
1767 /* in case reading has been interrupted earlier, discard context */
1768 svc.context.spbook.book = 0;
1769 svc.context.spbook.o_id = 0;
1770 /* count the number of known spells */
1771 for (n = 0; n < MAXSPELL; ++n)
1772 if (spellid(n) == NO_SPELL)
1773 break;
1774
1775 /* lose anywhere from zero to all known spells;
1776 if confused, use the worse of two die rolls */
1777 nzap = rn2(n + 1);
1778 if (Confusion) {
1779 i = rn2(n + 1);
1780 if (i > nzap)
1781 nzap = i;
1782 }
1783 /* good Luck might ameliorate spell loss */
1784 if (nzap > 1 && !rnl(7))
1785 nzap = rnd(nzap);
1786
1787 /*
1788 * Forget 'nzap' out of 'n' known spells by setting their memory
1789 * retention to zero. Every spell has the same probability to be
1790 * forgotten, even if its retention is already zero.
1791 *
1792 * Perhaps we should forget the corresponding book too?
1793 *
1794 * (3.4.3 removed spells entirely from the list, but always did
1795 * so from its end, so the 'nzap' most recently learned spells
1796 * were the ones lost by default. Player had sort control over
1797 * the list, so could move the most useful spells to front and
1798 * only lose them if 'nzap' turned out to be a large value.
1799 *
1800 * Discarding from the end of the list had the virtue of making
1801 * casting letters for lost spells become invalid and retaining
1802 * the original letter for the ones which weren't lost, so there
1803 * was no risk to the player of accidentally casting the wrong
1804 * spell when using a letter that was in use prior to amnesia.
1805 * That wouldn't be the case if we implemented spell loss spread
1806 * throughout the list of known spells; every spell located past
1807 * the first lost spell would end up with new letter assigned.)
1808 */
1809 for (i = 0; nzap > 0; ++i) {
1810 /* when nzap is small relative to the number of spells left,
1811 the chance to lose spell [i] is small; as the number of
1812 remaining candidates shrinks, the chance per candidate
1813 gets bigger; overall, exactly nzap entries are affected */
1814 if (rn2(n - i) < nzap) {
1815 /* lose access to spell [i] */
1816 spellknow(i) = 0;
1817#if 0
1818 /* also forget its book */
1819 forget_single_object(spellid(i));

Callers 2

mhitm_ad_drinFunction · 0.85
forgetFunction · 0.85

Calls 4

rn2Function · 0.85
rnlFunction · 0.85
rndFunction · 0.85
exerciseFunction · 0.85

Tested by

no test coverage detected