Overall Statistics
Total Trades
1099
Average Win
0.35%
Average Loss
-0.13%
Compounding Annual Return
-4.771%
Drawdown
48.200%
Expectancy
0.360
Net Profit
-12.944%
Sharpe Ratio
0.034
Probabilistic Sharpe Ratio
3.392%
Loss Rate
63%
Win Rate
37%
Profit-Loss Ratio
2.72
Alpha
0.013
Beta
-0.008
Annual Standard Deviation
0.362
Annual Variance
0.131
Information Ratio
-0.211
Tracking Error
0.38
Treynor Ratio
-1.457
Total Fees
$1316.30
from Execution.ImmediateExecutionModel import ImmediateExecutionModel
from Portfolio.EqualWeightingPortfolioConstructionModel import EqualWeightingPortfolioConstructionModel

class NetNet(QCAlgorithm):

    def Initialize(self):
        self.SetStartDate(2015, 1, 1)  # Set Start Date
        self.SetEndDate(2017, 10, 31)
        self.SetCash(100000)  # Set Strategy Cash
        
        self.SetUniverseSelection(FineFundamentalUniverseSelectionModel(self.CoarseSelectionFunction, self.FineSelectionFunction, None, None))
        self.UniverseSettings.Resolution = Resolution.Daily
        self.SetSecurityInitializer(lambda x: x.SetDataNormalizationMode(DataNormalizationMode.Raw))
        
        self.SetAlpha(ConstantAlphaModel(InsightType.Price, InsightDirection.Up, timedelta(days=365)))
        
        self.SetPortfolioConstruction(EqualWeightingPortfolioConstructionModel(lambda time: None))
        self.Settings.RebalancePortfolioOnInsightChanges = True
        self.Settings.RebalancePortfolioOnSecurityChanges = False
        
        self.SetExecution(ImmediateExecutionModel())

        self.SetBenchmark("SPY")
        
        self.year = -1


    def OnData(self, data):
        '''OnData event is the primary entry point for your algorithm. Each new data point will be pumped in here.
            Arguments:
                data: Slice object keyed by symbol containing the stock data
        '''

        # if not self.Portfolio.Invested:
        #    self.SetHoldings("SPY", 1)


    # on 15 Jan, filter for securities with fundamental data
    def CoarseSelectionFunction(self, coarse):
        # if self.Time.month == 10 and self.Time.day == 18 and self.Time.year == 2018:
        if self.Time.year == self.year:
            return Universe.Unchanged
        self.year = self.Time.year
        return [ x.Symbol for x in coarse if x.HasFundamentalData ]
    
    
    # on 15 Jan, filter first for securities with shares and then filter a second time for net net stocks
    def FineSelectionFunction(self, fine):
        filtered = [ x for x in fine if ((x.FinancialStatements.BalanceSheet.CurrentAssets.ThreeMonths - x.FinancialStatements.BalanceSheet.TotalLiabilitiesAsReported.ThreeMonths - x.FinancialStatements.BalanceSheet.PreferredStock.ThreeMonths) > 0) and (x.FinancialStatements.BalanceSheet.OrdinarySharesNumber.ThreeMonths > 0) ]
        # filtered = [ x for x in filtered if (x.FinancialStatements.BalanceSheet.OrdinarySharesNumber.ThreeMonths > 0) ]
        # filtered = [ x for x in filtered if (x.FinancialStatements.BalanceSheet.PreferredStock.ThreeMonths > 0) ]
        filtered = [ x.Symbol for x in filtered if (x.Price / ((x.FinancialStatements.BalanceSheet.CurrentAssets.ThreeMonths - x.FinancialStatements.BalanceSheet.TotalLiabilitiesAsReported.ThreeMonths - x.FinancialStatements.BalanceSheet.PreferredStock.ThreeMonths) / x.FinancialStatements.BalanceSheet.OrdinarySharesNumber.ThreeMonths)) <= 0.66 ]
        
        # for x in filtered:
        #     self.Log("Symbol: " + str(x.Symbol))
        #     self.Log("Name: " + x.CompanyReference.LegalName)
        #     self.Log(str(self.Time.month) + str(self.Time.day) + str(self.Time.year))
        #     self.Log("Price: " + str(x.Price))
        #     self.Log("Current Assets: " + str(x.FinancialStatements.BalanceSheet.CurrentAssets.ThreeMonths))
        #     self.Log("Total Liabilities: " + str(x.FinancialStatements.BalanceSheet.TotalLiabilitiesAsReported.ThreeMonths))
        #     self.Log("Preferred Stock: " + str(x.FinancialStatements.BalanceSheet.PreferredStock.ThreeMonths))
        #     self.Log("Shares: " + str(x.FinancialStatements.BalanceSheet.OrdinarySharesNumber.ThreeMonths))
        # filtered = [ x.Symbol for x in filtered ]
        
        return filtered