Exemplo n.º 1
0
    def pandl_for_all_trading_rules_unweighted(self, delayfill=True):
        """
        Get the p&l for all trading rules; unweighted

        Each trading rule has capital in isolation

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurveGroup

        """

        self.log.terse("Calculating pandl for all trading rules unweighted")

        variations = self.get_entire_trading_rule_list()

        # already weighted, don't need to do again
        pandl_by_trading_rule_unweighted = [
            self.pandl_for_trading_rule(rulename, delayfill)
            for rulename in variations
        ]

        # this is a group of groups... will it work?
        pandl_all_rules = accountCurveGroup(pandl_by_trading_rule_unweighted,
                                            variations,
                                            capital=ARBITRARY_FORECAST_CAPITAL,
                                            weighted_flag=False)

        return pandl_all_rules
Exemplo n.º 2
0
    def portfolio_with_multiplier(self, delayfill=True, roundpositions=True):
        """
        Get the p&l for entire portfolio using multiplied "actual" capital

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :param roundpositions: Round positions to whole contracts
        :type roundpositions: bool

        :returns: accountCurve

        """

        self.log.terse("Calculating pandl for portfolio")
        capital = self.get_actual_capital(delayfill, roundpositions)
        instruments = self.get_instrument_list()
        port_pandl = [
            self.pandl_for_instrument_with_multiplier(
                instrument_code,
                delayfill=delayfill,
                roundpositions=roundpositions)
            for instrument_code in instruments
        ]

        port_pandl = accountCurveGroup(port_pandl,
                                       instruments,
                                       capital=capital,
                                       weighted_flag=True)

        return port_pandl
Exemplo n.º 3
0
    def pandl_for_instrument_rules(self, instrument_code, delayfill=True):
        """
        Get the p&l for one instrument over multiple forecasts; as % of arbitrary capital

        P&L are weighted by forecast weights and FDM

        KEY OUTPUT

        :param instrument_code: instrument to get values for
        :type instrument_code: str


        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurve

        >>> from pysystemtrade.systems.basesystem import System
        >>> from pysystemtrade.systems.tests.testdata import get_test_object_futures_with_portfolios
        >>> (portfolio, posobject, combobject, capobject, rules, rawdata, data, config)=get_test_object_futures_with_portfolios()
        >>> system=System([portfolio, posobject, combobject, capobject, rules, rawdata, Account()], data, config)
        >>>
        >>> system.accounts.pandl_for_instrument_rules_weighted("EDOLLAR").get_stats("sharpe")
        {'ewmac16': 0.6799720823590352, 'ewmac8': 0.69594671177102}
        """

        self.log.terse("Calculating pandl for instrument rules for %s" %
                       instrument_code,
                       instrument_code=instrument_code)

        forecast_rules = self.get_trading_rule_list(instrument_code)
        pandl_rules_unweighted = [
            self.pandl_for_instrument_forecast(instrument_code,
                                               rule_variation_name,
                                               delayfill=delayfill)
            for rule_variation_name in forecast_rules
        ]

        pandl_rules = [
            weighted(pandl_this_rule,
                     weighting=self.get_forecast_scaling_factor(
                         instrument_code, rule_variation_name))
            for (pandl_this_rule, rule_variation_name
                 ) in zip(pandl_rules_unweighted, forecast_rules)
        ]

        pandl_rules = accountCurveGroup(pandl_rules,
                                        forecast_rules,
                                        capital=ARBITRARY_FORECAST_CAPITAL,
                                        weighted_flag=True)

        return pandl_rules
Exemplo n.º 4
0
    def pandl_for_instrument_rules_unweighted(self,
                                              instrument_code,
                                              rule_list=None,
                                              delayfill=True):
        """
        Get the p&l for one instrument over multiple forecasts; as % of arbitrary capital

        All forecasting rules will have same expected std dev of returns; these aren't weighted

        KEY OUTPUT

        :param instrument_code: instrument to get values for
        :type instrument_code: str


        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurveGroup

        >>> from pysystemtrade.systems.basesystem import System
        >>> from pysystemtrade.systems.tests.testdata import get_test_object_futures_with_portfolios
        >>> (portfolio, posobject, combobject, capobject, rules, rawdata, data, config)=get_test_object_futures_with_portfolios()
        >>> system=System([portfolio, posobject, combobject, capobject, rules, rawdata, Account()], data, config)
        >>>
        >>> system.accounts.pandl_for_instrument_rules_unweighted("EDOLLAR").get_stats("sharpe")
        {'ewmac16': 0.6799720823590352, 'ewmac8': 0.69594671177102}
        """

        self.log.terse("Calculating pandl for instrument rules for %s" %
                       instrument_code,
                       instrument_code=instrument_code)

        if rule_list is None:
            rule_list = self.get_trading_rule_list(instrument_code)
        pandl_rules = [
            self.pandl_for_instrument_forecast(instrument_code,
                                               rule_variation_name,
                                               delayfill=delayfill)
            for rule_variation_name in rule_list
        ]

        pandl_rules = accountCurveGroup(pandl_rules,
                                        rule_list,
                                        capital=ARBITRARY_FORECAST_CAPITAL,
                                        weighted_flag=False)

        return pandl_rules
Exemplo n.º 5
0
    def pandl_across_subsystems(self, delayfill=True, roundpositions=False):
        """
        Get the p&l across subsystems (unweighted)

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :param roundpositions: Round positions to whole contracts
        :type roundpositions: bool

        :returns: accountCurve

        >>> from pysystemtrade.systems.basesystem import System
        >>> from pysystemtrade.systems.tests.testdata import get_test_object_futures_with_portfolios
        >>> (portfolio, posobject, combobject, capobject, rules, rawdata, data, config)=get_test_object_futures_with_portfolios()
        >>> system=System([portfolio, posobject, combobject, capobject, rules, rawdata, Account()], data, config)
        >>>
        >>> system.accounts.pandl_across_subsystems().to_frame().tail(5)
                     EDOLLAR      US10
        2015-12-07  0.001191 -0.005012
        2015-12-08  0.000448 -0.002395
        2015-12-09  0.000311 -0.002797
        2015-12-10 -0.002384  0.003957
        2015-12-11  0.004835 -0.007594
        """

        # Subsystems use entire capital
        capital = self.get_notional_capital()

        instruments = self.get_instrument_list()
        pandl_across_subsys = [
            self.pandl_for_subsystem(instrument_code,
                                     delayfill=delayfill,
                                     roundpositions=roundpositions)
            for instrument_code in instruments
        ]

        pandl = accountCurveGroup(pandl_across_subsys,
                                  instruments,
                                  capital=capital,
                                  weighted_flag=False)

        return pandl
Exemplo n.º 6
0
    def pandl_for_trading_rule_weighted(self,
                                        rule_variation_name,
                                        delayfill=True):
        """
        Get the p&l for one trading rule over multiple instruments; as % of total capital

        Within the trading rule the instrument returns are weighted by risk contribution

        :param rule_variation_name: rule to get values for
        :type rule_variation_name: str

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurveGroup

        """
        self.log.terse("Calculating pandl for trading rule %s" %
                       rule_variation_name)

        instrument_list = self.parent.get_instrument_list()
        instrument_list = [
            instr_code for instr_code in instrument_list
            if rule_variation_name in self.get_trading_rule_list(instr_code)
        ]

        # already weighted, don't need to do again
        pandl_by_instrument_weighted = [
            self.pandl_for_instrument_forecast_weighted(
                instr_code, rule_variation_name, delayfill)
            for instr_code in instrument_list
        ]

        pandl_rule = accountCurveGroup(pandl_by_instrument_weighted,
                                       instrument_list,
                                       capital=ARBITRARY_FORECAST_CAPITAL,
                                       weighted_flag=True)

        return pandl_rule
Exemplo n.º 7
0
    def pandl_for_trading_rule_unweighted(self,
                                          rule_variation_name,
                                          delayfill=True):
        """
        Get the p&l for one trading rule over multiple instruments; as % of arbitrary capital

        Within the trading rule the instrument returns are NOT weighted by instrument weight

        :param rule_variation_name: rule to get values for
        :type rule_variation_name: str

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurve

        """

        self.log.terse("Calculating pandl for trading rule (unweighted) %s" %
                       rule_variation_name)

        instrument_list = self.parent.get_instrument_list()
        instrument_list = [
            instr_code for instr_code in instrument_list
            if rule_variation_name in self.get_trading_rule_list(instr_code)
        ]

        pandl_by_instrument = [
            self.pandl_for_instrument_forecast(instr_code, rule_variation_name,
                                               delayfill)
            for instr_code in instrument_list
        ]

        pandl_rule = accountCurveGroup(pandl_by_instrument,
                                       instrument_list,
                                       capital=ARBITRARY_FORECAST_CAPITAL,
                                       weighted_flag=False)

        return pandl_rule
Exemplo n.º 8
0
    def portfolio(self, delayfill=True, roundpositions=True):
        """
        Get the p&l for entire portfolio

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :param roundpositions: Round positions to whole contracts
        :type roundpositions: bool

        :returns: accountCurve

        >>> from pysystemtrade.systems.basesystem import System
        >>> from pysystemtrade.systems.tests.testdata import get_test_object_futures_with_portfolios
        >>> (portfolio, posobject, combobject, capobject, rules, rawdata, data, config)=get_test_object_futures_with_portfolios()
        >>> system=System([portfolio, posobject, combobject, capobject, rules, rawdata, Account()], data, config)
        >>>
        >>> system.accounts.portfolio().ann_std()
        0.2638225179274214
        """

        self.log.terse("Calculating pandl for portfolio")
        capital = self.get_notional_capital()
        instruments = self.get_instrument_list()
        port_pandl = [
            self.pandl_for_instrument(instrument_code,
                                      delayfill=delayfill,
                                      roundpositions=roundpositions)
            for instrument_code in instruments
        ]

        port_pandl = accountCurveGroup(port_pandl,
                                       instruments,
                                       capital=capital,
                                       weighted_flag=True)

        return port_pandl
Exemplo n.º 9
0
    def pandl_for_trading_rule(self, rule_variation_name, delayfill=True):
        """
        Get the p&l for one trading rule over multiple instruments; as % of its risk contribution

        Within the trading rule the instrument returns are weighted by instrument weight

        :param rule_variation_name: rule to get values for
        :type rule_variation_name: str

        :param delayfill: Lag fills by one day
        :type delayfill: bool

        :returns: accountCurve

        """

        self.log.terse("Calculating pandl for trading rule %s" %
                       rule_variation_name)

        instrument_list = self.parent.get_instrument_list()
        instrument_list = [
            instr_code for instr_code in instrument_list
            if rule_variation_name in self.get_trading_rule_list(instr_code)
        ]

        # already weighted
        # capital on these will be the default
        pandl_by_instrument_weighted = [
            self.pandl_for_instrument_forecast_weighted(
                instr_code, rule_variation_name, delayfill)
            for instr_code in instrument_list
        ]

        # now we weight so total capital is correct
        capital_this_rule = self.get_capital_in_rule(rule_variation_name)

        def _cleanweightelement(capelement):
            if np.isnan(capelement):
                return 0.0
            if capelement == 0.0:
                return 0.0
            else:
                return 1.0 / capelement

        weight = [
            _cleanweightelement(capelement)
            for capelement in list(capital_this_rule.values)
        ]
        weight = pd.Series(weight, index=capital_this_rule.index)

        pandl_by_instrument_reweighted = [
            weighted(pandl_for_instrument, weight, allow_reweighting=True)
            for pandl_for_instrument in pandl_by_instrument_weighted
        ]

        pandl_rule = accountCurveGroup(pandl_by_instrument_reweighted,
                                       instrument_list,
                                       capital=ARBITRARY_FORECAST_CAPITAL,
                                       weighted_flag=True)

        return pandl_rule