Announcement

Collapse
No announcement yet.

Partner 728x90

Collapse

Static variables and class recompile

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Static variables and class recompile

    Hi,

    during development I've noticed that when anything in NT is being recompiled static variables no longer function as expected. I'm just pointing out the issue to others.

    Example:

    Code:
        public class StaticTest : Indicator
        {
            private static string staticText;
            protected override void OnStateChange()
            {
                if (State == State.SetDefaults)
                {
                    Description                                    = @"Static values test";
                    Name                                        = "StaticTest";
                    Calculate                                    = Calculate.OnBarClose;
                    IsOverlay                                    = false;
                    DisplayInDataBox                            = false;
                    DrawOnPricePanel                            = false;
                    DrawHorizontalGridLines                        = true;
                    DrawVerticalGridLines                        = true;
                    PaintPriceMarkers                            = false;
                    ScaleJustification                            = NinjaTrader.Gui.Chart.ScaleJustification.Right;
                    //Disable this property if your indicator requires custom values that cumulate with each new market data event.
                    //See Help Guide for additional information.
                    IsSuspendedWhileInactive                    = true;
                    Text                    = string.Empty;
                }
                else if (State == State.Configure)
                {
                }
            }
    
            protected override void OnBarUpdate()
            {
                if(State != State.Realtime) {
                    return;
                }
    
                if(staticText == null) {
                    staticText = Text;
                }
    
                Print(String.Format("Instrument: {0} Text: {1}", Instrument.FullName, staticText));
            }
    
            #region Properties
            [NinjaScriptProperty]
            [Display(Name="Text", Order=1, GroupName="Parameters")]
            public string Text
            { get; set; }
            #endregion
        }
    For showcasing the behavior two 15 second charts with different instruments are created, one with Text set to 1, the other with Text set to 2.

    Output:
    Code:
    Instrument: NQ 03-20 Text: 1
    Instrument: GC 04-20 Text: 1
    Now some code is recompiled, it does not matter if it is the StaticTest indicator or something else. Then we reload the chart with Text 2 while not touching the other one.


    Output:
    Code:
    Instrument: NQ 03-20 Text: 1
    Instrument: GC 04-20 Text: 2
    In my opinion this happens because the instance of the indicator of the reloaded chart now resides in a new class loader context(maybe not the correct terminology) and the Text 1 indicator instance lives on in another.

    If this is not preventable people using code with static values should be aware of issues, maybe there is a workaround although I don't thing there needs to be one.
    In case such a workaround exists, if logic managing the static values is changed, NT would have to be restarted.
    I can imagine that it could be handled via IPC for simple values but passing object references would be more difficult.
    Last edited by MojoJojo; 03-05-2020, 11:24 PM.

    #2
    Hello MojoJojo,

    Thank you for the post and observation.

    While I can't comment on the inner mechanics of the compile in relation to static I will provide a quick note regarding using static. In general we do not suggest using static in NinjaScript as there are generally no use cases which require that type of development. You can certainly use static in your own development because it is part of C# however static does run against the general design pattern of NinjaScript so there may be some lapses with that use.

    In the sample you have shown the indicator instance on two separate instruments would be expected to have the same property value which can be set by either script. This is generally a bad thing when programming in NinjaScript as that goes against the general design pattern or expectations of the NinjaScript Host/Hosted pattern and isolation. There is also no sync between two scripts loading so you could potentially see them load or work differently with each reload. You are additionally using Realtime which each instrument is independent, the print could vary between reloads.

    If the intention was to share a constant value between two indicators a Partial class or addon class may be a better location for that type of code. If the intention was to otherwise share a value between scripts at all times there is currently no suggestion for that type of development. NinjaScript is a Parent <-> child based development system meaning a parent always calls a child and passes data through its constructor or retrieves a value using a plot/property. There are currently no design patterns where scripts can run concurrently and also communicate such as two separate indicators talking between each other.



    I look forward to being of further assistance.

    Comment


      #3
      Hello Jessie,

      thank you for your advice. You are right that using static variables is often bad form. My intent was to shed some light on the topic, it's not a bug.
      NT has made it very easy to write code and test it without restarting the platform, having to be more careful with static values is just a minor drawback that will pop up under very certain conditions and the average NT user won't encounter it. If one is aware of the limitation, using static values is no problem however I wouldn't distribute code to other users who're lacking the knowledge.

      Don't mind me brainstorming here a bit, let's say I wanted to write a share service that interacts with a database, would it not be much much much much more efficient to have a persistent database connection open at all time instead of opening one for each read/write. Could this qualify as a use case? I know it's not per se required and opening more than one connection would not result in disaster.

      Of course following the design patterns is best most of the time,
      My indicator example was not meant to be realistic but as simple as possible, for something more useful the MySharedMethodsAddonExample is much better.
      Last edited by MojoJojo; 03-06-2020, 01:45 PM.

      Comment


        #4
        Hello MojoJojo,

        It may be slightly more efficient depending on the scenario but that also comes with extra stipulations outside of the standard script design. In general there are no concepts of having a single source of data within NinjaScript like this, most everything you do relies on how the platform reloads your items based on the actions being completed.

        All types are instance based surrounding how the compile system works which means most concepts rely on the script being totally inclusive or not to rely on external items. The state system is a good way to observe that system, the OnStateChange override is put in place to guide the instance along the correct path in all use cases. When you work outside of that system you can run into unexpected situations or other issues surrounding compiles and when the script is being terminated and reloaded.

        We are using C# so there are likely some items you can do to increase performance with the objects you use however that heavily relates to what you are specifically doing. 99% of users will never require static for any use case so these topics will heavily relate to your specific goal and if that would actually help with efficiency in that use case.

        You can try it both ways and see if there is a noticeable improvement comparing tests. If there is not much improvement I would not suggest trying to add that in as static because that goes beyond the normal state system for a negligible performance improvement. If that otherwise helps with performance greatly, sure go ahead and use it with your existing knowledge of static. You just need to keep in mind the nuances or program your own solutions when it works in odd ways based on the existing reload system.




        I look forward to being of further assistance.



        Comment


          #5
          Thanks for the elaborate answer Jesse, have a good weekend.

          Comment

          Latest Posts

          Collapse

          Topics Statistics Last Post
          Started by Geovanny Suaza, 02-11-2026, 06:32 PM
          0 responses
          647 views
          0 likes
          Last Post Geovanny Suaza  
          Started by Geovanny Suaza, 02-11-2026, 05:51 PM
          0 responses
          369 views
          1 like
          Last Post Geovanny Suaza  
          Started by Mindset, 02-09-2026, 11:44 AM
          0 responses
          108 views
          0 likes
          Last Post Mindset
          by Mindset
           
          Started by Geovanny Suaza, 02-02-2026, 12:30 PM
          0 responses
          572 views
          1 like
          Last Post Geovanny Suaza  
          Started by RFrosty, 01-28-2026, 06:49 PM
          0 responses
          573 views
          1 like
          Last Post RFrosty
          by RFrosty
           
          Working...
          X