import numpy as np
import pandas as pd
from pandas.io.pytables import HDFStore
from datetime import datetime, timedelta
import rs

# from scipy import optimize
# from scipy.optimize import basinhopping

# class investigates assets for given window with discrete sortino first then with continuous

class Selector:  

    def __init__(self, data, date=None, window=2*365, maxAssets=10, mode=None):    
        self.data = data       
        self.date = date
        self.assets = pd.Series(data.assetList) 
        self.market = self.data.assets["^GSPC"]['excess_daily_ret']
        self.window = window
        self.maxAssets = maxAssets        
        self.returns = pd.DataFrame() 
        self.mode = mode
        print "Selection initializated, mode:", mode

    def select(self):
        for symbol in self.assets:    
            self.returns[symbol] = self.data.assets[symbol]["excess_daily_ret"][self.date-timedelta(days=self.window):self.date].dropna()            
        
        # check if data are valid - from self.date - window to self date
        # drop assets that have more than one NaN in window
        self.returns.dropna(axis=1, inplace=True)             

        # save vix for later if needed
        vix = self.returns["^VIX"]   

        #update portfolio assets in index   
        self.selection = pd.DataFrame(index=list(self.returns.columns.values), columns=['sortino_d'])   
        print "Starting preselection with", self.assets.count(), "assets"

        #firstly select 2 times maxassets sorted by discrete sortino
        self.selection['sortino_d'] = self.selection.index.map(lambda symbol : rs.sortino_d(self.returns[symbol]))         
        self.selection = self.selection.sort("sortino_d", ascending=False)[:self.maxAssets*2] 
        self.returns = self.returns[self.selection.index]   

        print "Preselected assets:"
        print self.selection

        # selection with discrete sortino
        self.selection['sortino_c'] = self.selection.index.map(lambda symbol : rs.sortino_c(self.returns[symbol]))         
        self.selection = self.selection.sort("sortino_c", ascending=False)[:self.maxAssets] 
        self.returns = self.returns[self.selection.index]   
             
        if not "^VIX" in self.selection.index and self.mode == "includeVix":
            print "Adding VIX"
            self.selection = self.selection.append(pd.Series({'sortino_d':rs.sortino_d(vix), 'sortino_c':rs.sortino_c(vix)},name='^VIX'))
            self.returns.append(vix)


        print rs.sortino_c(self.returns.sum())
        print "Selected assets:"
        print self.selection        

        return self.selection