
特定口座で購入した投資信託を売却してから新NISAへ移管するべきかどうかをシミュレーションするPythonプログラム
当サイトではアフィリエイト広告を利用しています
家族から相談を受けまして、特定口座で保持している投資信託を新NISAへ売却して移管するべきかどうか聞かれました。
色々と条件が複雑槽だったので、Pythonでプログラムを書いてシミュレーションしてみました。
検討するべき内容
特定口座で購入した投資信託を移管するべきかどうかを検討するにあたり、様々な条件が付きまといます。
- 含み益がどれくらいで売却時にいくら課税されるのか
- 新NISAへ積み立てる金額
- 新NISAで積立可能な期間
- 新NISA枠を埋め切れるか
- 想定利回り
色々と検討するべき内容が多かったので、話を整理したもののエクセルで集計することをあきらめ、以下のようなPythonプログラムを作成しました。
プログラムのソースコード
定数部分で想定するアセットの利回りやすでに所持する特定口座の元本・評価額、投資年数や積立額、シミュレーション年数等を設定しています。
それが完了したらresult.csv
に比較結果を書き出します。
import pandas as pd
PROFIT_YEAR = 0.05 # 想定年利
PROFIT_MONTH = PROFIT_YEAR / 12
TOKUTEI_BASE = 1_500_000 # 特定口座元本
TOKUTEI_HYOUKA = 2_000_000 # 特定口座評価額
TAX_RATE = 0.20315
MONTHLY = 200_000 # 投資月額
YEAR = 40 # シミュレーション年数
YEAR_AVAIL = 25 # 投資可能年数
NISA_LIMIT = 18_000_000 # NISA枠上限
def sim(
tokutei_org: float, # 特定口座元本
tokutei_eval: float, # 特定口座評価額
transfer: bool, # 初年度移管するかどうか
) -> tuple[list[float], list[float], list[float], list[float], list[float]]:
_l_nisa_org = [0]
_l_nisa_eval = [0]
_l_nisa_remain = [NISA_LIMIT]
_l_tokutei_org = [tokutei_org]
_l_tokutei_eval = [tokutei_eval]
if transfer is True:
ts_amount = TOKUTEI_HYOUKA - (TOKUTEI_HYOUKA - TOKUTEI_BASE) * TAX_RATE
else:
ts_amount = 0
for _y in range(YEAR):
_remain = _l_nisa_remain[-1]
_sum = _l_nisa_eval[-1]
_org = _l_nisa_org[-1]
_tokutei_sum = _l_tokutei_eval[-1]
_tokutei_org = _l_tokutei_org[-1]
for _m in range(12):
# 月利を計算
_sum *= 1 + PROFIT_MONTH
# 移管計算
if transfer is True and _y == 0 and _m == 0:
_remain -= ts_amount
_sum += ts_amount
_org += ts_amount
_tokutei_org = 0
_tokutei_sum = 0
# 移管後に月利計算
_tokutei_sum *= 1 + PROFIT_MONTH
# 投資可能年数を超えているかどうか
if _y >= YEAR_AVAIL:
continue
if _remain > MONTHLY:
_sum += MONTHLY
_org += MONTHLY
_remain -= MONTHLY
else:
_sum += _remain
_org += _remain
_tokutei_sum += MONTHLY - _remain
_tokutei_org += MONTHLY - _remain
_remain = 0
_l_nisa_org.append(_org)
_l_nisa_eval.append(_sum)
_l_nisa_remain.append(_remain)
_l_tokutei_eval.append(_tokutei_sum)
_l_tokutei_org.append(_tokutei_org)
return _l_nisa_org, _l_nisa_eval, _l_nisa_remain, _l_tokutei_org, _l_tokutei_eval
def main():
# 維持する場合
nisa_org, nisa_eval, nisa_remain, tokutei_org, tokutei_eval = sim(
TOKUTEI_BASE, # 特定口座元本
TOKUTEI_HYOUKA, # 特定口座評価額
False, # 初年度移管しない
)
df = pd.DataFrame(
{
"維持:新NISA元本": nisa_org,
"維持:新NISA評価額": nisa_eval,
"維持:新NISA残枠": nisa_remain,
"維持:特定口座元本": tokutei_org,
"維持:特定口座評価額": tokutei_eval,
}
)
df["維持:評価額合計"] = df["維持:新NISA評価額"] + df["維持:特定口座評価額"]
df["維持:払出時合計"] = (
df["維持:評価額合計"]
- (df["維持:特定口座評価額"] - df["維持:特定口座元本"]) * TAX_RATE
)
# 初期に売却して移管する場合
nisa_org, nisa_eval, nisa_remain, tokutei_org, tokutei_eval = sim(
TOKUTEI_BASE, # 特定口座元本
TOKUTEI_HYOUKA, # 特定口座評価額
True, # 初年度移管する
)
df["移管:新NISA元本"] = nisa_org
df["移管:新NISA評価額"] = nisa_eval
df["移管:新NISA残枠"] = nisa_remain
df["移管:特定口座元本"] = tokutei_org
df["移管:特定口座評価額"] = tokutei_eval
df["移管:評価額合計"] = df["移管:新NISA評価額"] + df["移管:特定口座評価額"]
df["移管:払出時合計"] = (
df["移管:評価額合計"]
- (df["移管:特定口座評価額"] - df["移管:特定口座元本"]) * TAX_RATE
)
df["維持>移管"] = df["維持:払出時合計"] > df["移管:払出時合計"]
df["維持-移管"] = df["維持:払出時合計"] - df["移管:払出時合計"]
df.to_csv("result.csv", float_format="%.0f")
if __name__ == "__main__":
main()
結論
色々と定数部分を変えてみましたが、ざっとみたところ以下のようになっていそうです。
- 含み益がある程度出ていて、10年以内に新NISA枠を埋め切れるなら移管しないほうがいい
- 含み益が出ていても20年以上新NISA枠を埋めきれないなら移管したほうがいい
- 含み益が出てないならば違約して移管したほうがいい
この辺りは含み益のパーセンテージや想定利回り、投資可能期間と積立年数など変数が色々とあるので、ご自身の条件に合わせて検討いただくのが一番かと思いました。
適宜ご自分の条件に上記プログラムを書き換えて調査してみるとよいかもしれません。
なお、このプログラムは筆者が興味本位で作成した信頼性の薄い素人コードですので、これによって生じたいかなる結果に関して責任は負いかねますのであしからず。