Lean  $LEAN_TAG$
Constraint.cs
1 /*
2  * QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
3  * Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14 */
15 
16 using Newtonsoft.Json;
17 using Newtonsoft.Json.Linq;
18 using QuantConnect.Util;
19 using System;
20 using Newtonsoft.Json.Converters;
21 using Newtonsoft.Json.Serialization;
22 
24 {
25  /// <summary>
26  /// A backtest optimization constraint.
27  /// Allows specifying statistical constraints for the optimization, eg. a backtest can't have a DrawDown less than 10%
28  /// </summary>
29  public class Constraint : Objective
30  {
31  /// <summary>
32  /// The target comparison operation, eg. 'Greater'
33  /// </summary>
34  [JsonConverter(typeof(StringEnumConverter))]
35  public ComparisonOperatorTypes Operator { get; set; }
36 
37  /// <summary>
38  /// Empty Constraint constructor
39  /// </summary>
40  public Constraint()
41  {
42 
43  }
44 
45  /// <summary>
46  /// Creates a new instance
47  /// </summary>
48  public Constraint(string target, ComparisonOperatorTypes @operator, decimal? targetValue) : base(target, targetValue)
49  {
50  Operator = @operator;
51 
52  if (!TargetValue.HasValue)
53  {
54  throw new ArgumentNullException(nameof(targetValue), Messages.Constraint.ConstraintTargetValueNotSpecified);
55  }
56  }
57 
58  /// <summary>
59  /// Asserts the constraint is met
60  /// </summary>
61  public bool IsMet(string jsonBacktestResult)
62  {
63  if (string.IsNullOrEmpty(jsonBacktestResult))
64  {
65  throw new ArgumentNullException(nameof(jsonBacktestResult), $"Constraint.IsMet(): {Messages.OptimizerObjectivesCommon.NullOrEmptyBacktestResult}");
66  }
67 
68  var token = Objectives.Target.GetTokenInJsonBacktest(jsonBacktestResult, Target);
69  if (token == null)
70  {
71  return false;
72  }
73 
74  return Operator.Compare(
75  token.Value<string>().ToNormalizedDecimal(),
76  TargetValue.Value);
77  }
78 
79  /// <summary>
80  /// Pretty representation of a constraint
81  /// </summary>
82  public override string ToString()
83  {
84  return $"{Target} '{Operator}' {TargetValue.Value}";
85  }
86  }
87 }