예제 #1
0
    async def analysis(self):

        self.proforma = await self.portfolio.calc_proforma(self.db, self.start_time, folioPerformance=False)
        self.coins = self.portfolio.coins
        self.coins_ts = [f.Performance for f in self.coins]
        self.weights = [float(a['weight']) for a in self.allocs]
        
        self.regs = [SimpleReg(fts,self.proforma)[0] for fts in self.coins_ts]
        self.tot_beta = sum([b * w for b,w in zip(self.regs, self.weights)])
        #contribition to risk
        crisks = [b * w / self.tot_beta for b,w in zip(self.regs, self.weights)]
        self.crisk = [toDecimal(crisk) for crisk in crisks]
        
        self.port_mean, self.port_std, self.port_var = self.calc_port_stats(self.proforma)
        #marginal var
        self.marginal_vars = []
        for i in range(len(self.coins)):
            var = await self.marginal_var(i)
            self.marginal_vars.append(toDecimal(var))
        #return contributions
        self.coin_returns = [mean(ts) for ts in self.coins_ts]
        
        self.coin_ret_contrib = [r * w   for r,w in zip(self.coin_returns, self.weights)]
        self.port_er = sum(self.coin_ret_contrib)
        c_rets = [r / self.port_er for r in self.coin_ret_contrib]
        self.c_ret = [toDecimal(ret) for ret in c_rets]
        self.N = len(self.coins)
예제 #2
0
    def calculate_stats(self):
        self.basicStats = BasicStats(self.perf)
        n = len(self.data_frame.columns)
        self.n_benchmarks = n - 1
        self.mddser = self.basicStats.mdd_ser
        self.mdd_dates = self.mddser.index
        self.mdds = self.mddser.values
        styleTime = (datetime.utcfromtimestamp(int(
            self.start_at))) if self.start_at else ""

        def day_date(date_str):
            if len(str(date_str)) == 1:
                return "0%s" % str(date_str)
            else:
                return str(date_str)

        def compare_date(d):
            return (
                int(str(d.year) + day_date(d.month) + day_date(d.day)) >= int(
                    str(styleTime.year) + day_date(styleTime.month) +
                    day_date(styleTime.day))) if styleTime else False

        if n > 1:
            bench_values = self.data_frame[self.data_frame.columns[1]].values
            bench_series = Series(data=bench_values,
                                  index=self.data_frame.index)
            self.bench_stats = BasicStats(bench_series)
            self.bench_mdd = self.bench_stats.mdd_ser
            self.mdd_res = sorted([
                (d, m, b)
                for d, m, b in zip(self.mdd_dates, self.mdds, self.bench_mdd)
            ])
            self.mdd_reses = [[{
                "year": str(d.year),
                "month": day_date(d.month),
                "day": day_date(d.day)
            }, m, b,
                               compare_date(d)] for d, m, b in self.mdd_res]
        else:
            self.mdd_res = sorted([(d, m)
                                   for d, m in zip(self.mdd_dates, self.mdds)])
            self.mdd_reses = [[{
                "year": str(d.year),
                "month": day_date(d.month),
                "day": day_date(d.day)
            },
                               toDecimal(m),
                               compare_date(d)] for d, m in self.mdd_res]

        self.var = toDecimal(self.basicStats.var)
예제 #3
0
    def __init__(self, y, x):
        self.ts_y = y

        if type(x) is list:
            self.ts_x = x
        else:
            self.ts_x = [x]
        self.all_series = self.ts_x.copy()
        self.all_series.insert(0, self.ts_y)
        self.common_data = align_series(self.all_series)
        self.columns = self.common_data.columns
        self.Y = self.common_data[self.columns[0]].values
        self.X = self.common_data[self.columns[1:]].values
        self.X = sm.add_constant(self.X)
        self.model = sm.OLS(self.Y, self.X)
        self.reg_results = self.model.fit()
        betas = list(self.reg_results.params)[1:]
        self.betas = [toDecimal(b) for b in betas]
        self.pvalues = self.reg_results.pvalues[1:]
        self.alpha = self.reg_results.params[0]
        self.rsq_adj = self.reg_results.rsquared_adj
        self.rsq = self.reg_results.rsquared
        self.coin_vol = var(self.Y)
        if len(self.ts_x) > 1:
            self.factor_cov = cov(self.X[:, 1:], rowvar=False)
            betas = [float(betas) for betas in self.betas]
            self.fcmtr = matmul(self.factor_cov, betas)
            self.crisk = [
                b * v / self.coin_vol for (b, v) in zip(betas, self.fcmtr)
            ]
        else:
            self.factor_cov = [cov(self.X[:, 1])]
            self.crisk = [self.rsq]
        self.crisk.append(1 - sum(self.crisk))
        self.crisk_cum = cumsum(self.crisk)
예제 #4
0
 def get_histogram(self):
     """
         Calculate Histogram
     """
     cnt, bins = histogram(self.values, bins='sqrt')
     self.histogram_data = list([toDecimal(b), int(c)]
                                for b, c in zip(bins[1:], cnt))
예제 #5
0
def get_histogram(values, gt=True, val=10):
    """
        Calculate Histogram
    """
    cnt, bins = histogram(values, bins='sqrt')
    datas = list([toDecimal(b), int(c)] for b, c in zip(bins[1:], cnt))
    data_list = []
    val_num = 0
    per = 0
    for d in datas:
        if gt:
            if val < float(d[0]):
                per = 9.999
                val_num += int(d[1])
            else:
                data_list.append(d)
        else:
            if val > float(d[0]):
                per = -0.9999
                val_num += int(d[1])
            else:
                data_list.append(d)
    data_list.append([toDecimal(per), int(val_num)])
    return data_list
예제 #6
0
    async def analysis(self):
        if self.isPortfolio:
            self.item = await self.db.get_portfolio(self.item_id,
                                                    modify_num=30)
            if self.item:
                performance_data = self.item.folio_ts
                modify_at = self.item.modify_at
            else:
                performance_data = Series()
                modify_at = None
        else:
            self.item = await self.db.get_coin(self.item_id)
            modify_at = None
            if self.item:
                performance_data = self.item.Performance
            else:
                performance_data = Series()

        self.risk_factors = await self.db.get_risk_factors(
            self.tickers, modify_at, self.isPortfolio)
        self.factor_ts = [r.Performance for r in self.risk_factors]
        self.coin_ts = performance_data
        self.reg_analysis = RegressionAnalysis(self.coin_ts, self.factor_ts)
        self.factor_names = [r.Name for r in self.risk_factors]
        self.factor_names.append("Unexplained")
        self.common_data = self.reg_analysis.common_data
        self.N = len(self.factor_names)
        self.T = len(self.common_data)
        self.rolling_reg = []
        self.IsPortfolio = self.isPortfolio
        if self.T >= 12:
            window = 12
            if self.T >= 36:
                window = 24
            dates = self.common_data.index

            def day_date(date_str):
                if len(str(date_str)) == 1:
                    return "0%s" % str(date_str)
                else:
                    return str(date_str)

            styleTime = (datetime.utcfromtimestamp(int(
                self.started_at))) if self.started_at else ""
            if styleTime:
                month = day_date(styleTime.month)
                day = day_date(styleTime.day)
                styleDate = str(styleTime.year) + month + day
            else:
                styleDate = ""

            def compare_date(d):
                return (int(str(d["year"]) + str(d["month"]) + str(d["day"]))
                        >= int(styleDate)) if styleDate else False

            for t0 in range(window, self.T):
                idx = range(t0 - window, t0)
                rolldates = dates[idx]
                ser = lambda c: Series(data=self.common_data.iloc[idx, c],
                                       index=rolldates)
                y_ts = ser(0)
                x_ts = [ser(c + 1) for c in range(self.N - 1)]
                rollreg = RegressionAnalysis(y_ts, x_ts)
                rollreg_dict = {
                    "betas": rollreg.betas,
                    "crisk": [toDecimal(crisk) for crisk in rollreg.crisk]
                }
                d = rolldates[-1]
                rolldate = {
                    "year": str(d.year),
                    "month": day_date(d.month),
                    "day": day_date(d.day)
                }
                self.rolling_reg.append(
                    [rolldate, rollreg_dict,
                     compare_date(rolldate)])
            self.rolling_window = window
            self.RollingT = len(self.rolling_reg)
예제 #7
0
    def calculate_vami_chart(self):
        self.cum_values = (self.data_frame + 1).cumprod().values
        data = []
        T = len(self.data_frame)
        for t in range(T):
            arr = []
            cum_list = self.cum_values[t, :].tolist()
            cum_list = [toDecimal(cu) for cu in cum_list]
            for cum in cum_list:
                arr.append(cum)
            data.append(arr)
        dates = self.data_frame.index

        pydate_array = dates.to_pydatetime()
        date_only_array = np.vectorize(lambda s: s.strftime('%Y-%m-%d'))(
            pydate_array)
        date_only_series = pd.Series(date_only_array)
        dates = date_only_series.to_dict().values()

        dates = [{
            "year": date.split("-")[0],
            "month": date.split("-")[1],
            "day": date.split("-")[2]
        } for date in dates]
        self.vami_cols = self.data_frame.columns.values.tolist()
        self.vami_data = list(zip(dates, data))

        def day_date(date_str):
            if len(str(date_str)) == 1:
                return "0%s" % str(date_str)
            else:
                return str(date_str)

        styleTime = (datetime.utcfromtimestamp(int(
            self.start_at))) if self.start_at else ""
        if styleTime:
            month = day_date(styleTime.month)
            day = day_date(styleTime.day)
            styleDate = str(styleTime.year) + month + day
        else:
            styleDate = ""

        info_data = {"isStart": True, "start_val": None}

        def compare_date(d, infoData):
            try:
                time_str = str(d[0]["year"]) + str(d[0]["month"]) + str(
                    d[0]["day"])
                val = (int(time_str) >= int(styleDate)) if styleDate else False
                if val and infoData["isStart"]:
                    infoData["isStart"] = False
                    infoData["start_val"] = d[1]
                val = True if int(time_str) == int(styleDate) else val
                compare_data = [d[0], d[1], val]
            except:
                compare_data = d
            return compare_data

        self.vami_data = [
            compare_date(list(item), info_data) for item in self.vami_data
        ]
        if info_data["start_val"] and float(info_data["start_val"][0]):
            self.vami_data_rate = [[
                item[0],
                [
                    toDecimal(float(item[1][0]) /
                              float(info_data["start_val"][0]),
                              style="0.000")
                ], item[2]
            ] for item in self.vami_data]
        else:
            self.vami_data_rate = self.vami_data

        values = [toDecimal(val) for val in self.values]
        self.hist_chart_items = list(zip(dates, values))
        self.hist_chart_data = [
            compare_date(list(item), info_data)
            for item in self.hist_chart_items
        ]
예제 #8
0
from analytics.basicstats import BasicStats
from analytics.capture_ratios import CaptureRatios
from analytics.correlation_analysis import CorrelationAnalysis
from analytics.helper import StatsHelper
from analytics.regression_analysis import RegressionAnalysis
from analytics.time_series import align_series

from coin_application.portfolios import dao as folios_dao
from coin_application.reports import dao as report_dao
from datalib.coin import CoinPerformance
from datalib.datalib import Connection
from lib.utils import toDecimal, getErrorMsg, toPreTimestamp, _
from logger.client import error
from settings import windows

f2d = lambda a: [round(toDecimal(x), 4) for x in a]
"""
    Calculate non-linear sensitivity / convexity regression
"""


def calc_tmy(fts, benchts):
    common_data = align_series([fts, benchts])
    common_data.columns = ['Y', 'X']
    common_data['XY'] = common_data['X']**2
    y = common_data.iloc[:, 0].values
    x = common_data.iloc[:, 1:].values
    x = sm.add_constant(x)

    model = sm.OLS(y, x)
    res = model.fit()