fork download
  1. lex_by_file( FileName ) :-
  2. get_input_from_file( FileName, TokenList ),
  3. lex( TokenList, OutputList ),
  4. %write_output( OutputList ), !.
  5. maplist(writeln,OutputList),!.
  6.  
  7. %% atom_number(atom, number)
  8. lex([],[]).
  9. lex(['int' | T], ['TYPE: int' | R]) :- lex(T, R).
  10. lex(['bool' | T], ['TYPE: bool'] | R) :- lex(T, R).
  11. lex([',' | T], ['COMMA: ,'] | R) :- lex(T, R).
  12. lex([X | T], [X | R]) :- lex(T, R).
  13.  
Success #stdin #stdout #stderr 0.03s 7176KB
stdin
import yfinance as yf
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt

# 1. 基础设置
tickers = ['SPY', 'EWH', 'ASHR', 'BTC-USD', 'GLD', 'AGG']
# 你的标准配置 (Base Weights)
base_weights = {
    'SPY': 0.30, 'EWH': 0.25, 'ASHR': 0.10, 
    'BTC-USD': 0.05, 'GLD': 0.10, 'AGG': 0.20
}
initial_capital = 7000000

# 2. 获取数据 (过去 10 年)
print("正在下载数据并构建罗盘...")
data = yf.download(tickers, start="2014-01-01", end="2025-01-01")['Adj Close'].dropna()

# 3. 计算核心指标 (罗盘的指针)
# Dalio Axis: 趋势 (MA200)
ma200 = data.rolling(window=200).mean()

# Marks Axis: 情绪 (RSI 14)
delta = data.diff()
gain = delta.where(delta > 0, 0).rolling(window=14).mean()
loss = -delta.where(delta < 0, 0).rolling(window=14).mean()
rs = gain / loss
rsi = 100 - (100 / (1 + rs))
rsi = rsi.fillna(50)  # 填充 NaN

# 重新索引并前向填充,确保与 data 对齐
ma200 = ma200.reindex(data.index).ffill()
rsi = rsi.reindex(data.index).ffill()

# 4. 回测循环
portfolio_value = []
cash = initial_capital
shares = {t: 0 for t in tickers}

# 获取月末日期
monthly_dates = data.resample('M').last().index.normalize()
data_index_normalized = data.index.normalize()

for date in data.index:
    # 当前投资组合价值
    current_value = cash + sum(shares[t] * data.loc[date, t] for t in tickers)
    portfolio_value.append(current_value)

    # 仅在月底进行罗盘检查和调仓
    if date.normalize() in monthly_dates:
        target_weights = base_weights.copy()

        for t in ['SPY', 'EWH', 'ASHR', 'BTC-USD']:  # 仅针对风险资产
            if date not in ma200.index or date not in rsi.index:
                continue
            price = data.loc[date, t]
            ma = ma200.loc[date, t]
            r_val = rsi.loc[date, t]

            # 跳过 NaN
            if pd.isna(ma) or pd.isna(r_val):
                target_weights[t] = base_weights[t]
                continue

            is_expansion = price > ma
            is_fear = r_val < 35
            is_greed = r_val > 75

            # Q2: 绝望区 (抄底)
            if not is_expansion and is_fear:
                target_weights[t] = base_weights[t] * 1.2
            # Q1: 泡沫区 (止盈)
            elif is_expansion and is_greed:
                target_weights[t] = base_weights[t] * 0.5
            # Q4: 崩溃/冬藏区 (止损)
            elif not is_expansion and not is_fear:
                target_weights[t] = 0.0
            # Q3: 趋势区 (持有)
            else:
                target_weights[t] = base_weights[t]

        # 可选:检查总权重是否超过 1.0,这里我们允许现金吸收
        total_assets = cash + sum(shares[t] * data.loc[date, t] for t in tickers)
        for t in tickers:
            target_amt = total_assets * target_weights.get(t, base_weights[t])
            shares[t] = target_amt / data.loc[date, t]

        # 更新现金
        invested = sum(shares[t] * data.loc[date, t] for t in tickers)
        cash = total_assets - invested

# 5. 结果计算与展示
portfolio_series = pd.Series(portfolio_value, index=data.index)
total_years = (portfolio_series.index[-1] - portfolio_series.index[0]).days / 365.25
cagr = (portfolio_series.iloc[-1] / initial_capital) ** (1 / total_years) - 1
drawdown = portfolio_series / portfolio_series.cummax() - 1
max_dd = drawdown.min()

print(f"【双因子罗盘策略 (Dalio x Marks)】")
print(f"年化收益率 (CAGR): {cagr:.2%}")
print(f"最大回撤 (Max Drawdown): {max_dd:.2%}")
print(f"期末总资产: {portfolio_series.iloc[-1]:,.0f}")

# 绘图
plt.figure(figsize=(12, 6))
portfolio_series.plot(title='Dynamic Cycle Strategy (Dalio + Marks)')
plt.ylabel('Portfolio Value')
plt.xlabel('Date')
plt.grid(True)
plt.show()
stdout

	
stderr
ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: Can't ignore goal at this port
ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: Can't ignore goal at this port
ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: Can't ignore goal at this port
ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: Can't ignore goal at this port
ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: '$runtoplevel'/0: Undefined procedure: program/0
   Exception: (3) program ? ERROR: Unknown option (h for help)
   Exception: (3) program ? ERROR: Unknown option (h for help)
   Exception: (3) program ? ERROR: Unknown option (h for help)
   Exception: (3) program ? % Break level 1

ERROR: Syntax error: Illegal start of term
ERROR: 'SPY': 0.30, 'EWH': 0.25, 'ASHR': 0.10, 
    'BTC-USD': 0.05, 'GLD': 0.10, 'AGG': 0.20
ERROR: ** here **
ERROR: 
}
initial_capital = 7000000

# 2 . 

ERROR: Syntax error: Operator expected
ERROR: 获取数据
ERROR: ** here **
ERROR:  (过去 10 年)
print("正在下载数据并构建罗盘...")
data = yf.download(tickers, start="2014-01-01", end="2025-01-01")['Adj Close'].dropna()

# 3 . 

ERROR: Syntax error: Operator expected
ERROR: 计算核心指标
ERROR: ** here **
ERROR:  (罗盘的指针)
# Dalio Axis: 趋势 (MA200)
ma200 = data.rolling(window=200).mean()

# Marks Axis: 情绪 (RSI 14)
delta = data.diff()
gain = delta.where(delta > 0, 0).rolling(window=14).mean()
loss = -delta.where(delta < 0, 0).rolling(window=14).mean()
rs = gain / loss
rsi = 100 - (100 / (1 + rs))
rsi = rsi.fillna(50)  # 填充 NaN

# 重新索引并前向填充,确保与 data 对齐
ma200 = ma200.reindex(data.index).ffill()
rsi = rsi.reindex(data.index).ffill()

# 4 . 

ERROR: Syntax error: Operator expected
ERROR: 回测循环
ERROR: ** here **
ERROR: 
portfolio_value = []
cash = initial_capital
shares = {t: 0 for t in tickers}

# 获取月末日期
monthly_dates = data.resample('M').last().index.normalize()
data_index_normalized = data.index.normalize()

for date in data.index:
    # 当前投资组合价值
    current_value = cash + sum(shares[t] * data.loc[date, t] for t in tickers)
    portfolio_value.append(current_value)

    # 仅在月底进行罗盘检查和调仓
    if date.normalize() in monthly_dates:
        target_weights = base_weights.copy()

        for t in ['SPY', 'EWH', 'ASHR', 'BTC-USD']:  # 仅针对风险资产
            if date not in ma200.index or date not in rsi.index:
                continue
            price = data.loc[date, t]
            ma = ma200.loc[date, t]
            r_val = rsi.loc[date, t]

            # 跳过 NaN
            if pd.isna(ma) or pd.isna(r_val):
                target_weights[t] = base_weights[t]
                continue

            is_expansion = price > ma
            is_fear = r_val < 35
            is_greed = r_val > 75

            # Q2: 绝望区 (抄底)
            if not is_expansion and is_fear:
                target_weights[t] = base_weights[t] * 1.2
            # Q1: 泡沫区 (止盈)
            elif is_expansion and is_greed:
                target_weights[t] = base_weights[t] * 0.5
            # Q4: 崩溃/冬藏区 (止损)
            elif not is_expansion and not is_fear:
                target_weights[t] = 0.0
            # Q3: 趋势区 (持有)
            else:
                target_weights[t] = base_weights[t]

        # 可选:检查总权重是否超过 1.0,这里我们允许现金吸收
        total_assets = cash + sum(shares[t] * data.loc[date, t] for t in tickers)
        for t in tickers:
            target_amt = total_assets * target_weights.get(t, base_weights[t])
            shares[t] = target_amt / data.loc[date, t]

        # 更新现金
        invested = sum(shares[t] * data.loc[date, t] for t in tickers)
        cash = total_assets - invested

# 5 . 

ERROR: Stream user_input:225:9 Syntax error: Unexpected end of file
% Exit break level 1
   Exception: (3) program ? EOF: exit