Combining Filters

Like factors, filters can be combined. Combining filters is done using the & (and) and | (or) operators. For example, let's say we want to screen for securities that are in the top 10% of average dollar volume and have a latest close price above \$20. To start, let's make a high dollar volume filter using an AverageDollarVolume factor and percentile_between:

In [1]:
from zipline.pipeline import Pipeline
from zipline.research import run_pipeline
from zipline.pipeline.data import EquityPricing
from zipline.pipeline.factors import SimpleMovingAverage, AverageDollarVolume
In [2]:
dollar_volume = AverageDollarVolume(window_length=30)
high_dollar_volume = dollar_volume.percentile_between(90, 100)

Note: percentile_between is a Factor method returning a Filter.

Next, let's create a latest_close factor and define a filter for securities that closed above $20:

In [3]:
latest_close = EquityPricing.close.latest
above_20 = latest_close > 20

Now we can combine our high_dollar_volume filter with our above_20 filter using the & operator:

In [4]:
tradeable_filter = high_dollar_volume & above_20

This filter will evaluate to True for securities where both high_dollar_volume and above_20 are True. Otherwise, it will evaluate to False. A similar computation can be made with the | (or) operator.

If we want to use this filter as a screen in our pipeline, we can simply pass tradeable_filter as the screen argument.

In [5]:
def make_pipeline():

    mean_close_10 = SimpleMovingAverage(inputs=[EquityPricing.close], window_length=10)
    mean_close_30 = SimpleMovingAverage(inputs=[EquityPricing.close], window_length=30)

    percent_difference = (mean_close_10 - mean_close_30) / mean_close_30

    dollar_volume = AverageDollarVolume(window_length=30)
    high_dollar_volume = dollar_volume.percentile_between(90, 100)

    latest_close = EquityPricing.close.latest
    above_20 = latest_close > 20

    tradeable_filter = high_dollar_volume & above_20

    return Pipeline(
        columns={
            'percent_difference': percent_difference
        },
        screen=tradeable_filter
    )

When we run this, our pipeline output now only includes ~700 securities.

In [6]:
result = run_pipeline(make_pipeline(), start_date='2015-05-05', end_date='2015-05-05')
print(f'Number of securities that passed the filter: {len(result)}')
result
/tmp/zipline/zipline/pipeline/filters/filter.py:473: RuntimeWarning: invalid value encountered in less_equal
  return (lower_bounds <= data) & (data <= upper_bounds)
Number of securities that passed the filter: 764
Out[6]:
percent_difference
2015-05-05 00:00:00+00:00Equity(FIBBG000C2V3D6 [A])-0.000111
Equity(QI000000004076 [AABA])-0.017429
Equity(FIBBG005P7Q881 [AAL])0.007729
Equity(FIBBG000F7RCJ1 [AAP])-0.010067
Equity(FIBBG000B9XRY4 [AAPL])0.016827
Equity(FIBBG000G6GXC5 [AAXJ])0.030521
Equity(FIBBG000BHJWG1 [AAXN])0.102930
Equity(FIBBG0025Y4RY4 [ABBV])0.056309
Equity(FIBBG000MDCQC2 [ABC])0.006168
Equity(FIBBG000B9ZXB4 [ABT])0.011940
Equity(FIBBG000BHG9K0 [ACAD])0.046260
Equity(FIBBG000D9D830 [ACN])0.000050
Equity(FIBBG000TH6VB3 [ACWI])0.013665
Equity(FIBBG000BB5006 [ADBE])0.009546
Equity(FIBBG000BB6G37 [ADI])0.009294
Equity(FIBBG000BB6WG8 [ADM])0.015734
Equity(FIBBG000JG0547 [ADP])-0.002144
Equity(FIBBG000BFNR17 [ADS])0.014035
Equity(FIBBG000BM7HL0 [ADSK])-0.003913
Equity(FIBBG003641015 [ADT])-0.035293
Equity(FIBBG000B9X8C0 [AEE])-0.001014
Equity(FIBBG000DLVDK3 [AEM])0.026100
Equity(FIBBG000BB9KF2 [AEP])0.010302
Equity(FIBBG000FJLFX8 [AET])0.005026
Equity(FIBBG000BBBNC6 [AFL])-0.002246
Equity(FIBBG000Q123R0 [AGG])-0.002449
Equity(FIBBG000QY4ZD0 [AGIO])0.014116
Equity(FIBBG000FH8PX5 [AGN])-0.018802
Equity(FIBBG000TJ8XZ7 [AGNC])-0.014706
Equity(FIBBG0084GLX33 [AGNPA])-0.008787
......
Equity(FIBBG000BX3BL3 [WY])-0.015952
Equity(FIBBG000PV2L86 [WYND])-0.017520
Equity(FIBBG000LD9JQ8 [WYNN])-0.036634
Equity(FIBBG000BX3TD3 [X])0.008099
Equity(FIBBG000MQQ963 [XBI])-0.009229
Equity(FIBBG000D6L294 [XEC])0.015894
Equity(FIBBG000BCTQ65 [XEL])-0.003815
Equity(FIBBG000MQSW88 [XHB])-0.016861
Equity(FIBBG0019HMDR8 [XIV])0.074869
Equity(FIBBG000C9W1Y1 [XL])-0.000856
Equity(FIBBG000BHNNF7 [XLB])0.015039
Equity(FIBBG000BJ20S2 [XLE])0.027294
Equity(FIBBG000BJ29X7 [XLF])0.001787
Equity(FIBBG000BJ2RF7 [XLI])0.002891
Equity(FIBBG000BJ7007 [XLK])0.017854
Equity(FIBBG000C0F570 [XLNX])0.018251
Equity(FIBBG000BJ10N8 [XLP])-0.002459
Equity(FIBBG000BJ7G75 [XLU])0.003236
Equity(FIBBG000BHVSG6 [XLV])0.002032
Equity(FIBBG000BJ1MF9 [XLY])0.005515
Equity(FIBBG000GZQ728 [XOM])0.017215
Equity(FIBBG000BGB482 [XOP])0.027811
Equity(FIBBG000D80VV4 [XRT])-0.009868
Equity(FIBBG000Q2HM09 [YELP])-0.000711
Equity(FIBBG000BH3GZ2 [YUM])0.057707
Equity(FIBBG003H0XV18 [YY])0.060564
Equity(FIBBG000BKPL53 [ZBH])-0.007930
Equity(FIBBG000D13GN8 [ZG])0.003626
Equity(FIBBG0039320N9 [ZTS])-0.006740
Equity(FIBBG00VT0KNC3 [MTCH])0.020778

764 rows × 1 columns


Next Lesson: Masking