Quantopian's community platform is shutting down. Please read this post for more information and download your code.
Back to Community
Help with creating a new fundamental indicator

I'm pretty new to coding and am having the hardest time figuring out something that I'm guessing is pretty simple to do. I'm trying to calculate ROIC (return on invested capital). This is simply Net Income/Invested Capital both of which are available through the morning star darts set. This is what I have....
NI=Fundamentals.net_income_income_statement
IC=Fundamentals.invested_capital
ROC=NI/IC
This obviously doesn't work because the Bound Column data type. How do I get around this while still making sure that the data lines up correctly?
any help would be greatly appreciated
Thanks!

3 responses

G'day Newb!

You are fortunate that a community member asked a similar question - the attached sample codes may be what you are looking for!

Hope this helps.

This example deals with nans (not a number). It happens when the fundamental value is absent for certain stocks.
Around 40% of the original calculated values are nan without a screen.
They can be screened on your input values being used (the Two-value screen section) and then shows that the built-in Fundamentals.roic still has some nans. That's on stocks where your two fundamental inputs were ok, they had populated values. So your route might be better than the built-in.
Then the complete screen section just adds removal of Fundamentals.roic nans, and I called that ROIC_f for short.
The ROIC() class is looking at a window of time and doing forward fill as a way of dealing with nans.
So, maybe that'll help some too. One might wonder why the minimum values (ROC vs ROIC_f) are so different, by the way.
Run that and look at the logging window, it also shows specific stock highs and lows for each column, I didn't paste them here.

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
No screen  
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
        #screen  = NI.notnull() & IC.notnull(),  
        #screen  = NI.notnull() & IC.notnull() & ROIC_f.notnull(),

2019-01-03 05:45 log_data:146 INFO Stocks: 8688  
                      min                  mid               max  
    IC      -1848599000.0         4436131000.0               nan     NaNs 3247/8688  
    NI     -22769000000.0          123832000.0               nan     NaNs 3584/8688  
   ROC     -16295.4934498      0.0410566685425               nan     NaNs 3586/8688  
ROIC_f         -87.080808             0.035863               nan     NaNs 3473/8688  
 class     -16295.4934498     0.00941190521827     193.560874895

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
Two-value screen  
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
2019-01-03 05:45 log_data:146 INFO Stocks: 5102  
    pipe  = Pipeline(  
        screen  = NI.notnull() & IC.notnull(),  
        #screen  = NI.notnull() & IC.notnull() & ROIC_f.notnull(),

2019-01-03 05:45 log_data:146 INFO Stocks: 5102  
                      min                 mid                max  
    IC      -1848599000.0         758137000.0     565951000000.0  
    NI     -22769000000.0           5734000.0      18540000000.0  
   ROC     -16295.4934498     0.0107877060859       46.899068323  
ROIC_f         -87.080808            0.013287                nan     NaNs 230/5102  
 class     -16295.4934498     0.0107877060859       46.899068323

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
Complete screen  
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  
2019-01-03 05:45 log_data:146 INFO Stocks: 4872  
    pipe  = Pipeline(  
        #screen  = NI.notnull() & IC.notnull(),  
        screen  = NI.notnull() & IC.notnull() & ROIC_f.notnull(),

2019-01-03 05:45 log_data:146 INFO Stocks: 4872  
                      min                 mid                max  
    IC      -1848599000.0         759468000.0     565951000000.0  
    NI     -22769000000.0           5683000.0      18540000000.0  
   ROC     -16295.4934498     0.0105196594322       46.899068323  
ROIC_f         -87.080808            0.012086         165.954222  
 class     -16295.4934498     0.0105196594322       46.899068323  

Hi Gary Blue,

I routinely avoid the .fillna() or nanfill() methods in data series as the data fills have produced (for me anyway) misleading and unpredictable results. I prefer to .dropna() outright for reason of data hygiene - use only those data that fit the purpose to compute the factors. However, on occasions when I really must approximate the data gaps, I use the np.polyfit() method instead.