Пример #1
0
def exit_by_max_holding_time(
    mkt: MarketData,
    sig: Optional[Signal],
    entries: Trades,
    max_holding_time: pd.Timedelta,
    exit_condition: Callable[[pd.DataFrame, pd.Series, pd.Timestamp], bool],
) -> Trades:
    """Exit trade at max holding time or satisfying condition.

    Args:
        mkt: Market data
        sig: Signal data
        entries: Tuple of entry trades.
        max_holding_time: maximum holding time
        exit_condition: The entry is closed most closest time which
                        condition is `True`.
    Result:
        Trades
    """
    df = _concat(mkt, sig)

    def _exit_by_max_holding_time(
        trades: Trades,
        df: pd.DataFrame,
        max_holding_time: pd.Timedelta,
        exit_condition: Callable[[pd.DataFrame, pd.Series, pd.Timestamp],
                                 bool],
    ) -> Trades:

        indices = []  # type: List[pd.Timestamp]
        exits = []  # type: List[Tuple[float, int]]
        for i in trades.ids:
            trade = trades.get_trade(i)
            if trade.sum() == 0:
                continue

            idx = trade.index[0]

            start = max(idx, df.index[0])
            end = min(idx + max_holding_time, df.index[-1])

            df_exit = df.loc[start:end]
            transaction = _exit_transaction(df_exit, trade, exit_condition)

            indices.append(transaction.timestamp)
            exits.append((transaction.amount, i))

        df = pd.DataFrame(index=indices, data=exits, columns=["amount", "_id"])
        return from_dataframe(df, symbol, currency_unit)

    symbol = entries.symbol
    currency_unit = entries.currency_unit
    exits = _exit_by_max_holding_time(entries, df, max_holding_time,
                                      exit_condition)
    return concat([entries, exits])
Пример #2
0
def exit(
    mkt: MarketData,
    sig: Optional[Signal],
    entries: Trades,
    exit_condition: Callable[[pd.DataFrame, pd.Series], pd.Series],
) -> Trades:
    """Exit trade when satisfying condition.

    Args:
        mkt: Market data
        sig: Signal data
        entries: Tuple of entry trades.
        max_holding_time: maximum holding time
        exit_condition: The entry is closed most closest time which
                        condition is `True`.
    Result:
        Trades
    """
    df = _concat(mkt, sig)

    def _exit(
        trades: Trades,
        df: pd.DataFrame,
        exit_condition: Callable[[pd.DataFrame, pd.Series], pd.Series],
    ) -> pd.Series:

        indices = []  # type: List[pd.Timestamp]
        exits = []  # type: List[Tuple[float, int]]
        for i in trades.ids:
            trade = trades.get_trade(i)
            if trade.sum() == 0:
                continue

            idx = trade.index[0]
            df_exit = df[idx <= df.index]
            transaction = _exit_transaction(df_exit, trade, exit_condition)

            indices.append(transaction.timestamp)
            exits.append((transaction.amount, i))

        df = pd.DataFrame(index=indices, data=exits, columns=["amount", "_id"])

        return from_dataframe(df, symbol)

    symbol = entries.symbol
    exits = _exit(entries, df, exit_condition)
    return concat([entries, exits])
Пример #3
0
def test_concat(trades, expected_ids, refresh_id):
    trades1 = trades.copy()
    trades2 = trades.copy()
    result = module.concat([trades1, trades2], refresh_id)

    # check symbol
    expected = trades1.symbol
    assert result.symbol == expected

    # check len
    expected = len(trades1) + len(trades2)
    assert len(result) == expected

    # check ids
    expected = expected_ids
    assert result.ids == expected

    # check amount
    data = trades.amount * 2.0
    index = pd.date_range(start="2018-06-06", freq="1min", periods=len(data))
    expected = pd.Series(data=data, index=index, name="amount")
    pd.testing.assert_series_equal(result.amount, expected)