Changes

Jump to navigation Jump to search
Line 32: Line 32:  
* [https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/builtin-types/record record structs];
 
* [https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/builtin-types/record record structs];
 
* and support for ARM64 on macOS.
 
* and support for ARM64 on macOS.
 +
 +
===Hash set fields===
 +
For C# mod authors, the game now uses [https://www.bytehide.com/blog/hashset-csharp hash sets] for many list fields which expect unique values. That allows much more efficient O(1) read/write, prevents duplicate values, and simplifies common logic.
 +
 +
This affects:
 +
{| class="wikitable"
 +
|-
 +
! type
 +
! fields
 +
|-
 +
| <samp>Farmer</samp>
 +
| <samp>achievements</samp><br /><samp>dialogueQuestionsAnswered</samp><br /><samp>eventsSeen</samp><br /><samp>mailbox</samp><br /><samp>mailForTomorrow</samp><br /><samp>mailReceived</samp><br /><samp>professions</samp><br /><samp>secretNotesSeen</samp><br /><samp>songsHeard</samp>
 +
|-
 +
| <samp>FarmerTeam</samp>
 +
| <samp>broadcastedMail</samp>
 +
|}
 +
 +
Usage is very similar, and many list methods like <samp>Contains</samp> work the same way with hash sets. Here are the main differences:
 +
<ul>
 +
<li>Hash sets aren't ordered. For example, there's no guarantee that the first value when you enumerate it was the earliest one added.</li>
 +
<li><p>Hash sets can't be indexed. For example, you can no longer use <code>list[0]</code> to get the first value. You can still enumerate them, but in most cases you should use methods like <samp>Add</samp> or <samp>Contains</samp> instead.</p>
 +
 +
To remove multiple matching values from the set, you can use <samp>RemoveWhere</samp> instead:
 +
<syntaxhighlight lang="c#">
 +
// old code
 +
for (int i = Game1.player.mailbox.Count - 1; i >= 0; i--)
 +
{
 +
    if (Game1.player.mailbox[i].StartsWith("Example.ModId_"))
 +
        Game1.player.mailbox.RemoveAt(i);
 +
}
 +
 +
// new code
 +
Game1.player.mailbox.RemoveWhere(id => id.StartsWith("Example.ModId_"));
 +
</syntaxhighlight>
 +
 +
The game also adds a <samp>Peek()</samp> extension in the <samp>StardewValley.Extensions</samp> namespace to get the first value that would be enumerated. This is equivalent to the previous <samp>list[0]</samp>, except that the order may change when a value is added or removed.
 +
</li>
 +
<li>You no longer need to check before adding a value, since the hash set will ignore duplicates.</li>
 +
<li>The <samp>Add</samp> or <samp>Remove</samp> values return whether a value was added/removed, which lets you check at the same time. For example:
 +
<syntaxhighlight lang="c#">
 +
if (Game1.player.mailReceived.Add("BackpackTip")) // returns true if it wasn't in the set yet
 +
    Game1.addMailForTomorrow("pierreBackpack");
 +
</syntaxhighlight>
 +
</li>
 +
</ul>
    
==What's new for items==
 
==What's new for items==
translators
8,445

edits

Navigation menu