# Score adjudicated calls on real 1m option bars. Rules frozen in README_youtube.md before running. import sys,numpy as np,pandas as pd; sys.path.insert(0,'scripts'); from bars import bars LOT={'NIFTY':65,'SENSEX':20} def chg(Q,buy,sell): sv=sell*Q; bv=buy*Q; brk=40.0; stt=0.0015*sv; txn=0.0003503*(bv+sv); sebi=1e-6*(bv+sv); stamp=3e-5*bv; gst=0.18*(brk+txn+sebi) return (brk+stt+txn+sebi+stamp+gst)/Q def hm_add(hm,m): h,mm=map(int,hm.split(':')); t=h*60+mm+m; return f'{t//60:02d}:{t%60:02d}' def score(ix,date,strike,typ,entry_hm,sl,tg): g,ex,src=bars(ix,date,strike,typ) if g is None: return dict(status='not_scorable',why=src,expiry=ex) e_hm=hm_add(entry_hm,1); g=g[g.index>='09:15'] if e_hm>'15:14' or e_hm not in g.index: return dict(status='not_scorable',why='no_entry_bar',expiry=ex,src=src) w=g[(g.index>=e_hm)&(g.index<='15:15')]; ent=float(w.open.iloc[0])+0.5 stop=ent-sl; tgt=ent+tg; ex_px=None; why='time' for hm,r in w.iterrows(): if r.low<=stop: ex_px=stop; why='SL'; xt=hm; break if r.high>=tgt: ex_px=tgt; why='T'; xt=hm; break if ex_px is None: ex_px=float(w.close.iloc[-1]); xt=w.index[-1] ex_px-=0.5; c=chg(LOT[ix],ent,ex_px); net=ex_px-ent-c return dict(status='scored',expiry=ex,src=src,entry_bar=e_hm,entry_px=round(ent,2),exit_hm=xt,exit_reason=why,exit_px=round(ex_px,2),charges_pts=round(c,2),net_pts=round(net,2),R=round(net/sl,3))