Search Unity

  1. If you have experience with import & exporting custom (.unitypackage) packages, please help complete a survey (open until May 15, 2024).
    Dismiss Notice
  2. Unity 6 Preview is now available. To find out what's new, have a look at our Unity 6 Preview blog post.
    Dismiss Notice

I feel like I'm abusing delegates in C#. Am I doing this wrong? Should I stop?

Discussion in 'Scripting' started by RaymingW, Sep 14, 2019.

  1. RaymingW

    RaymingW

    Joined:
    Nov 11, 2017
    Posts:
    36
    During a game jam last week I realized how handy delegate is.

    Instead of getting a reference of a script and call the public function when a certain event occurs, I would create a delegate for the event-generating script and let other scripts I needed subscribe to that delegate.

    These saved me tons of hustle because:
    • I don't need to rewrite the event generating scripts every time I need a new script responds to the event. Just let the new scripts subscribed the delegate and its done.
    • I don't need to write codes for catching new components spawned into the scene.
    • Using this method I can reuse the event-generating scripts in whatever scene I wanted because the event-generating script doesn't need to care about what is in the scene since it doesn't hold any reference of the scripts it needs to control.
    After I finished the game, I realized how different my new game is compared to other games I have created. There are barely any scripts hold references to other scripts and I was even invoking delegate in Update() and FixedUpdate() function. It was a hassle unsubscribing every delegate when I destroy a script but everything else felt so easy to implement and clean.

    Is there something wrong with this way of architecture? When should I stop using delegates? Will there be performance issues if I were doing it on a large scale?
     
  2. Laperen

    Laperen

    Joined:
    Feb 1, 2016
    Posts:
    1,065
    The only real drawback of using delegates as events is, every connection you make to any event takes up some memory. Forgetting to unsubscribe an event can occur when you subscribe your events when a scene is loaded, but forgot to unsubscribe or clear one or a few events when unloading the scene, to go to a new scene or reloading the scene. All subscribers which you forgot to unsubscribe or clear remain in memory, and in the case of a reload you add even more subscribers to the event. This adds up quickly and can cause your game to lag and eventually come to a halt if you are not careful. I'm not sure if its possible to use too many events and subscribers to reach the point that it just lags from running normally, but I've encountered the rest of the above personally. Just be diligent about unsubscribing or clearing an event after its usefulness is fulfilled, and you should be fine
     
  3. Stardog

    Stardog

    Joined:
    Jun 28, 2010
    Posts:
    1,913
    No, you should use them more. And replace your long-winded delegates with Action/Func.

    This:
    Code (csharp):
    1. public delegate void EventHandler();
    2. public event EventHandler onSomethingHappened;
    Can be replaced by this:
    Code (csharp):
    1. public event Action onSomethingHappened;
    You call it like this
    Code (csharp):
    1. onSomethingHappened?.Invoke()
    if your project is using the latest .NET version.

    Watch these 3 videos -
     
  4. RaymingW

    RaymingW

    Joined:
    Nov 11, 2017
    Posts:
    36
    Thank you so much for your reply! Now I can use them without a hesitant.
     
  5. RaymingW

    RaymingW

    Joined:
    Nov 11, 2017
    Posts:
    36
    Thank you for sharing this awesome video for me. It is very helpful and answered a lot of questions I had about delegate
     
  6. RaymingW

    RaymingW

    Joined:
    Nov 11, 2017
    Posts:
    36
    What does "event" do when I declare an Action? Everything seems working just fine when I don't include it in my code.

    Edit:
    I found the answer.
    https://stackoverflow.com/questions/6259273/what-does-the-event-keyword-really-do
     
  7. palex-nx

    palex-nx

    Joined:
    Jul 23, 2018
    Posts:
    1,748
    It is easy to create in this manner, but it is also easy to get a mess of connections you can't control. While using delegates for events is good, a logic based on delegates will quickly grow out of control, when it becomes handler of handler of handler of handler and you just unable to mentally visualise and understand such deep and branchy call graph. Keep it clean, 1 level of handler. If you want to make event handler to invoke another event, consider using another approach, unless it's absolutely neccessary.
     
  8. RaymingW

    RaymingW

    Joined:
    Nov 11, 2017
    Posts:
    36
    Thanks, I'll keep that in mind.