public void LongPropertyPathAccess_StableBindingSimple()
        {
            const string scriptFunctionSourceCode = @"
import clr
def PropertyPathAccess(cascade) :
  return cascade.GetChild().GetChild().GetName()
";

            const int numberChildren       = 10;
            var       cascade              = new Cascade(numberChildren);
            var       cascadeStableBinding = new CascadeStableBinding(numberChildren);
            //var cascadeStableBinding = ObjectFactory.Create<CascadeStableBinding> (ParamList.Create (numberChildren));
            var cascadeLocalStableBinding = new CascadeLocalStableBinding(numberChildren);

            var cascadeGetCustomMemberReturnsAttributeProxyFromMap = new CascadeGetCustomMemberReturnsAttributeProxyFromMap(numberChildren);

            cascadeGetCustomMemberReturnsAttributeProxyFromMap.AddAttributeProxy("GetChild", cascade, _scriptContext);
            cascadeGetCustomMemberReturnsAttributeProxyFromMap.AddAttributeProxy("GetName", cascade, _scriptContext);


            var privateScriptEnvironment = ScriptEnvironment.Create();

            privateScriptEnvironment.Import(typeof(Cascade).Assembly.GetName().Name, typeof(Cascade).Namespace, typeof(Cascade).Name);

            var propertyPathAccessScript = new ScriptFunction <Cascade, string> (
                _scriptContext,
                ScriptLanguageType.Python,
                scriptFunctionSourceCode,
                privateScriptEnvironment,
                "PropertyPathAccess"
                );


            privateScriptEnvironment.ImportIifHelperFunctions();
            privateScriptEnvironment.SetVariable("GLOBAL_cascade", cascade);
            var expression = new ExpressionScript <Object> (
                _scriptContext,
                ScriptLanguageType.Python,
                "GLOBAL_cascade.GetChild().GetChild().GetName()",
                privateScriptEnvironment
                );


            //var nrLoopsArray = new[] { 1, 1, 10, 100, 1000, 10000, 100000, 1000000 };
            var nrLoopsArray = new[] { 1, 1, 10, 100, 1000, 10000 };

            ScriptingHelper.ExecuteAndTime("script function", nrLoopsArray, () => propertyPathAccessScript.Execute(cascade));
            ScriptingHelper.ExecuteAndTime("script function (stable binding)", nrLoopsArray, () => propertyPathAccessScript.Execute(cascadeStableBinding));
            ScriptingHelper.ExecuteAndTime("script function (local stable binding)", nrLoopsArray, () => propertyPathAccessScript.Execute(cascadeLocalStableBinding));
            ScriptingHelper.ExecuteAndTime("script function (from map)", nrLoopsArray, () => propertyPathAccessScript.Execute(cascadeGetCustomMemberReturnsAttributeProxyFromMap));
        }
        public void SimplePropertyAccess_GetCustomMember_AttributeProxyFromMap()
        {
            const string scriptFunctionSourceCode =
                @"
import clr
def PropertyPathAccess(cascade) :
  if cascade.GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetName() == 'C0' :
    return cascade.GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetChild().GetName()
  return 'FAILED'
";

            const int numberChildren = 10;
            var       cascade        = new Cascade(numberChildren);

            var cascadeGetCustomMemberReturnsAttributeProxyFromMap = new CascadeGetCustomMemberReturnsAttributeProxyFromMap(numberChildren);

            cascadeGetCustomMemberReturnsAttributeProxyFromMap.AddAttributeProxy("GetName", cascade, _scriptContext);
            cascadeGetCustomMemberReturnsAttributeProxyFromMap.AddAttributeProxy("GetChild", cascade, _scriptContext);

            var privateScriptEnvironment = ScriptEnvironment.Create();

            privateScriptEnvironment.Import(typeof(Cascade).Assembly.GetName().Name, typeof(Cascade).Namespace, typeof(Cascade).Name);

            var propertyPathAccessScript = new ScriptFunction <Cascade, string> (
                _scriptContext,
                ScriptLanguageType.Python,
                scriptFunctionSourceCode,
                privateScriptEnvironment,
                "PropertyPathAccess"
                );

            //var nrLoopsArray = new[] { 1, 1, 10, 100, 1000, 10000, 100000, 1000000 };
            //var nrLoopsArray = new[] { 1, 1, 10, 100, 1000, 10000, 100000 };
            var nrLoopsArray = new[] { 10 };

            ScriptingHelper.ExecuteAndTime("script function", nrLoopsArray, () => propertyPathAccessScript.Execute(cascade));
            ScriptingHelper.ExecuteAndTime("script function (AttributeProxyFromMap)", nrLoopsArray, () => propertyPathAccessScript.Execute(cascadeGetCustomMemberReturnsAttributeProxyFromMap));
        }