সমাধান — অধ্যায় ৫.৩ · ANOVA & Experimental Design¶
অধ্যায় ফাইল:
part-5-modeling/05-03-anova-experimental-design.md(§৭ অনুশীলনী)-এর সব প্রশ্নের পূর্ণ সমাধান। সব সংখ্যাগত ফল NumPy/SciPy দিয়ে যাচাই ওstatsmodels-এর সাথে মিলিয়ে দেখা হয়েছে; seeded কোড reproducible। চলমান উদাহরণ — agricultural field trial, seednp.random.default_rng(20260619), \(n=120\): তিন fertilizer (A,B,C) \(\times\) দুই irrigation (low,high), প্রতি cell-এ \(20\) plot;crop\(=30+\{A{:}0,B{:}5,C{:}8\}+\{\text{low}{:}0,\text{high}{:}6\}+4\cdot[\![C\,\&\,\text{high}]\!]+\mathcal N(0,4^2)\)।স্মারক — canonical সংখ্যা (seed 20260619): one-way
crop~fert— group means \(\bar y_A=32.404,\ \bar y_B=38.103,\ \bar y_C=43.969\), grand \(\bar y=38.158\); group sd \(s_A=5.315,\ s_B=6.135,\ s_C=7.259\); \(\mathrm{SSB}=2674.99,\ \mathrm{SSW}=4624.17,\ \mathrm{SST}=7299.15\); \(df=(2,117)\); \(\mathrm{MSB}=1337.49,\ \mathrm{MSW}=39.52\); \(F=33.84,\ p=2.529\times10^{-12}\)। two-waycrop~fert*irrig— fert \(F=84.80\), irrig \(F=172.10\), interaction \(F=3.54\ (p=0.0322)\), residual \(\mathrm{SS}=1798.03,\ df=114\); cell means A-low \(28.55\), A-high \(36.26\), B-low \(33.78\), B-high \(42.43\), C-low \(37.88\), C-high \(50.06\)। Tukey: \(A\)–\(B\) \(5.70\), \(A\)–\(C\) \(11.56\), \(B\)–\(C\) \(5.87\), তিনটাই reject।
ক · ধারণাগত (conceptual)¶
সমাধান ১ (★)¶
আপাত-বৈপরীত্যের সমাধান: আমরা দুই উৎস থেকে \(\sigma^2\) আনুমান করি আর তাদের তুলনা করি।
- \(\mathrm{SSW}\) (within) শুধু group-এর ভেতরের ছড়ানো মাপে — group-গড় যাই হোক, এর সাথে সম্পর্ক নেই। তাই \(\mathrm{MSW}=\mathrm{SSW}/(n-k)\) সর্বদা শুধু noise \(\sigma^2\)-এর estimate (সমাধান ১২-তে প্রমাণ)।
- \(\mathrm{SSB}\) (between) group-গড়গুলো grand mean থেকে কত ছড়ানো তা মাপে। group-গড়ও এলোমেলোভাবে দোলে (sampling noise), তাই \(\mathrm{MSB}\)-তে noise তো থাকেই — প্লাস group-গড় সত্যিই আলাদা হলে একটা অতিরিক্ত signal-term।
তাই যুক্তিটা signal-to-noise: $\(\mathbb E[\mathrm{MSW}]=\sigma^2,\qquad \mathbb E[\mathrm{MSB}]=\sigma^2+\frac{1}{k-1}\sum_g n_g(\mu_g-\bar\mu)^2.\)$
\(H_0:\mu_A=\mu_B=\mu_C\) সত্য হলে signal-term \(=0\), দুটোই \(\sigma^2\)-এর estimate, তাই $\(F=\frac{\mathrm{MSB}}{\mathrm{MSW}}\approx 1.\)$ গড় আলাদা হলে numerator-এ signal যোগ হয়ে \(\mathrm{MSB}>\mathrm{MSW}\), তাই \(F\gg1\)। চলমান data-তে \(F=33.84\) — অর্থাৎ between-group ছড়ানো noise-এর ৩৩ গুণেরও বেশি, যা \(H_0\)-এর সাথে অসঙ্গতিপূর্ণ। এক বাক্যে: "গড় আলাদা?" প্রশ্নের উত্তর আসে "between-variance কি within-variance-এর চেয়ে বেশি বড়, যতটা শুধু chance দিয়ে আশা করা যায়?" — তাই variance তুলনা করেই গড়ের সিদ্ধান্ত।
সমাধান ২ (★)¶
সমস্যার নাম: multiple comparisons → family-wise error rate (FWER) inflation।
প্রতিটা test-এ Type I error rate \(\alpha=0.05\) মানে "একটা সত্য null কে ভুলভাবে reject করার সম্ভাবনা \(5\%\)"। কিন্তু একাধিক test একসাথে চালালে অন্তত একটায় ভুল করার সম্ভাবনা জমে বাড়ে। সব null সত্য ও test (আনুমানিক) স্বাধীন ধরলে: $\(\text{FWER}=1-(1-\alpha)^m,\qquad m=\binom{k}{2}.\)$
- \(k=3\): \(m=\binom32=3\), তাই \(\text{FWER}=1-0.95^3=1-0.857=0.143\approx \mathbf{14.3\%}\) — নামমাত্র \(5\%\)-এর প্রায় তিন গুণ।
- \(k=5\): \(m=\binom52=\mathbf{10}\) জোড়া-test, \(\text{FWER}=1-0.95^{10}=1-0.599=\mathbf{0.401}\) — অর্থাৎ সব গড় সমান হলেও \(40\%\) সম্ভাবনায় অন্তত একটা "মিথ্যা পার্থক্য" পাওয়া যাবে।
(বাস্তবে pairwise test-গুলো পুরোপুরি স্বাধীন নয় বলে সঠিক FWER কিছুটা আলাদা, কিন্তু inflation-এর গুণগত চিত্র একই — দ্রুত বাড়ে।) ANOVA এই সমস্যা এড়ায় একটিমাত্র global \(F\)-test দিয়ে (\(H_0:\) সব গড় সমান), যার নিজস্ব Type I rate ঠিক \(\alpha\)-তে থাকে। \(F\) reject করলে তবেই post-hoc (Tukey HSD) দিয়ে জোড়া খোঁজা হয়, আর Tukey সেই দ্বিতীয় ধাপের FWER-ও \(0.05\)-এ ধরে রাখে।
সমাধান ৩ (★★)¶
(ক) main vs interaction। - main effect = একটা factor-এর গড় প্রভাব, অন্য factor-এর সব level জুড়ে averaged। যেমন "fertilizer পাল্টালে গড়ে ফলন কত বদলায় (irrigation যাই হোক)"। - interaction effect = একটা factor-এর প্রভাব অন্য factor-এর level-ভেদে বদলায় কিনা। interaction শূন্য হলে প্রভাবগুলো additive (প্রতিটি factor স্বাধীনভাবে যোগ হয়); শূন্য না হলে একটার প্রভাব অন্যটার উপর নির্ভর করে।
(খ) এই interaction-এর অর্থ — fertilizer C-র সুবিধা low ও high-এ এক নয়। irrigation low\(\to\)high গেলে ফলন-বৃদ্ধি:
| fertilizer | low | high | বৃদ্ধি (high − low) |
|---|---|---|---|
| \(A\) | \(28.55\) | \(36.26\) | \(\mathbf{7.71}\) |
| \(B\) | \(33.78\) | \(42.43\) | \(\mathbf{8.65}\) |
| \(C\) | \(37.88\) | \(50.06\) | \(\mathbf{12.18}\) |
additive হলে তিনটা বৃদ্ধি সমান হতো (\(\approx6\), irrigation-এর main effect)। কিন্তু \(C\)-তে বৃদ্ধি \(12.18\) — \(A\)-র (\(7.71\)) প্রায় দেড় গুণ। অর্থাৎ ভালো সার (\(C\)) আর ভালো সেচ (high) একসাথে দিলে আলাদা-আলাদা যোগফলের চেয়ে বেশি ফলন — এ-ই synergy, ঠিক যেটা DGP-তে \((C,\text{high})\)-এ \(+4\) যোগ করে ঢোকানো হয়েছিল। \(F_{\text{int}}=3.54,\ p=0.032\) বলছে এই পার্থক্য chance-এর চেয়ে বড়।
(গ) interaction থাকলে main effect একা বিভ্রান্তিকর কেন। "fertilizer C গড়ে \(X\) বাড়ায়" বললে শ্রোতা ভাবে প্রভাবটা সব পরিস্থিতিতে এক। কিন্তু interaction মানে প্রভাবটা irrigation-এর উপর নির্ভর করে — high-এ \(C\)-র বাড়তি সুবিধা বেশি, low-এ কম। তাই সৎ উপসংহার হলো conditional: "\(C\)-র সুবিধা irrigation high-এ সবচেয়ে বেশি"। interaction significant হলে main effect-কে একা না-বলে আগে cell-mean-চিত্র (interaction plot) দেখানোই রীতি।
সমাধান ৪ (★★)¶
dummy/indicator encoding। \(A\)-কে reference ধরে দুটো indicator: \(D_B=1\) যদি group \(=B\) নয়তো \(0\); \(D_C=1\) যদি group \(=C\)। তাহলে $\(y=\beta_0+\beta_1 D_B+\beta_2 D_C+\varepsilon.\)$ প্রতিটা group-এ fitted মান বসিয়ে দেখি: - group \(A\): \(D_B=D_C=0\Rightarrow \mathbb E[y]=\beta_0\), তাই \(\boxed{\beta_0=\mu_A}\) (reference গড়)। - group \(B\): \(D_B=1,D_C=0\Rightarrow \mathbb E[y]=\beta_0+\beta_1=\mu_B\), তাই \(\boxed{\beta_1=\mu_B-\mu_A}\)। - group \(C\): \(D_C=1\Rightarrow \mathbb E[y]=\beta_0+\beta_2=\mu_C\), তাই \(\boxed{\beta_2=\mu_C-\mu_A}\)।
অর্থাৎ coefficient-গুলো group-গড়ের পার্থক্য (reference-এর সাপেক্ষে)। চলমান data-তে \(\beta_0=32.40\), \(\beta_1=38.10-32.40=5.70\), \(\beta_2=43.97-32.40=11.57\) — যা Tukey-র \(A\)–\(B\) ও \(A\)–\(C\) difference-এর সমান।
\(F\)-test সমতা। ANOVA-র \(H_0:\mu_A=\mu_B=\mu_C\) \(\Leftrightarrow\) \(\mu_B-\mu_A=0\) এবং \(\mu_C-\mu_A=0\) \(\Leftrightarrow\) \(\beta_1=\beta_2=0\) — যা ঠিক ৫.২-এর overall \(F\)-test (intercept বাদে সব slope একসাথে শূন্য)। সংখ্যাতেও এক: regression-এর overall \(F\) আর one-way ANOVA-র \(F\) হুবহু \(33.84\) (\(df=2,117\))। তাই ANOVA = categorical predictor-সহ regression — আলাদা theory নয়, একই OLS-যন্ত্র।
সমাধান ৫ (★★)¶
(ক) LINE-এর সাথে মিল।
| ANOVA অনুমান | LINE অক্ষর | অর্থ |
|---|---|---|
| group-গুলো ও observation স্বাধীন | I (Independence) | error পরস্পর-uncorrelated |
| group-এর মধ্যে error Normal | N (Normality) | \(\varepsilon_{gi}\sim\) Normal |
| সব group-এ variance সমান | E (Equal variance) | homogeneity / homoscedasticity |
Linearity (L) এখানে স্বয়ংক্রিয়ভাবে সিদ্ধ — dummy-model-এ প্রতিটি group-এর জন্য আলাদা mean parameter, তাই "রৈখিকতা" তুচ্ছভাবে সত্য।
(খ) variance অসম হলে ঝুঁকি। \(F\)-statistic-এর null distribution হুবহু \(F_{k-1,n-k}\) হয় শুধু যখন সব group-এ একই \(\sigma^2\)। variance খুব আলাদা হলে এই distribution আর সঠিক থাকে না, তাই \(p\)-value বিকৃত (সাধারণত — বিশেষত unbalanced হলে — Type I error প্রকৃত \(\alpha\) থেকে সরে যায়)। এখানে \(s_A=5.32,\ s_C=7.26\), অনুপাত \(s_C/s_A\approx1.37\) (variance-অনুপাত \(\approx1.86\)) — মাঝারি, সাধারণ rule-of-thumb ("largest sd < 2× smallest") মানছে, তাই \(F\)-test যুক্তিসঙ্গতভাবে নিরাপদ। (severe হলে Welch's ANOVA বা log-transform বিকল্প।)
(গ) balanced design কেন robust। তত্ত্ব ও simulation দুই-ই দেখায় cell-size সমান হলে (\(n_g\) সব এক) \(F\)-test variance-অসমতার প্রতি অনেক কম সংবেদনশীল — Type I error প্রকৃত \(\alpha\)-র খুব কাছে থাকে। unbalanced হলেই বিকৃতি বড় হয় (বড় variance যদি ছোট group-এ পড়ে, error inflate; বড় group-এ পড়লে deflate)। তাই সমান \(n=20\) একটা সচেতন design-গুণ — randomization/blocking-এর সাথে এটিই ভালো পরীক্ষা-নকশার অংশ।
খ · গণনামূলক (computational)¶
সমাধান ৬ (★)¶
balanced (\(n_g=40\) সবার) বলে সব হিসাব সরল।
(ক) grand mean (সমান \(n\) বলে group-গড়ের সরল গড়): $\(\bar y=\frac{32.40+38.10+43.97}{3}=\frac{114.47}{3}=38.16.\ \checkmark\)$
(খ) \(\mathrm{SSB}=\sum_g n_g(\bar y_g-\bar y)^2\): $\(\mathrm{SSB}=40\big[(32.40-38.16)^2+(38.10-38.16)^2+(43.97-38.16)^2\big]\)$ $\(=40\big[(-5.76)^2+(-0.06)^2+(5.81)^2\big]=40\big[33.18+0.0036+33.76\big]=40(66.94)\approx \mathbf{2675.0}.\ \checkmark\)$
(গ) \(\mathrm{SSW}=\sum_g(n_g-1)s_g^2\) (কারণ \(s_g^2=\frac1{n_g-1}\sum_i(y_{gi}-\bar y_g)^2\Rightarrow \sum_i(\cdot)^2=(n_g-1)s_g^2\)): $\(\mathrm{SSW}=39\big[5.315^2+6.135^2+7.259^2\big]=39\big[28.25+37.64+52.69\big]=39(118.57)\approx \mathbf{4624.2}.\ \checkmark\)$
(ঘ) df ও MS: $\(df_B=k-1=2,\quad df_W=n-k=120-3=117;\)$ $\(\mathrm{MSB}=\frac{2675.0}{2}=1337.5,\qquad \mathrm{MSW}=\frac{4624.2}{117}=39.52.\)$
(ঙ) \(F\): $\(F=\frac{\mathrm{MSB}}{\mathrm{MSW}}=\frac{1337.5}{39.52}=\mathbf{33.84}.\ \checkmark\)$
সব সংখ্যা canonical-এর সাথে (rounding-সীমার মধ্যে) হুবহু মিলেছে — অর্থাৎ raw data ছাড়াই শুধু group-summary থেকে পুরো ANOVA table পুনর্গঠন সম্ভব।
সমাধান ৭ (★)¶
(ক) critical value \(F_{0.95;\,2,117}\approx 3.07\)। observed \(F=33.84\gg 3.07\), তাই \(H_0\) জোরালোভাবে বাতিল (\(\alpha=0.05\)-এ — আসলে যেকোনো বাস্তব \(\alpha\)-তেই)।
from scipy import stats
print(stats.f.ppf(0.95, 2, 117)) # 3.0738...
print(stats.f.sf(33.84, 2, 117)) # 2.53e-12
(খ) \(p\)-value-র সঠিক ব্যাখ্যা। \(p\approx2.5\times10^{-12}\) মানে: "যদি তিন fertilizer-এর সত্যিকারের গড় ফলন একই হতো, তবে নিছক sampling-চাঞ্চল্যে এত বড় (বা বড়তর) \(F\) পাওয়ার সম্ভাবনা প্রায় \(2.5\times10^{-12}\)।" এটি "গড় সমান হওয়ার সম্ভাবনা" নয়, "\(H_0\) ভুল হওয়ার সম্ভাবনা" নয় — এ দুটোই সাধারণ ভুল। এত ক্ষুদ্র \(p\) বলছে data \(H_0\)-র সাথে চরম অসঙ্গতিপূর্ণ।
(গ) এখন কী জানি / জানি না। \(F\) reject করায় আমরা জানি "অন্তত একজোড়া গড় আলাদা" — কিন্তু কোন জোড়া (শুধু \(C\) আলাদা? নাকি তিনটাই?), তা \(F\) বলে না। তাই পরের ধাপ = post-hoc multiple comparison (Tukey HSD, সমাধান ৯), যা FWER নিয়ন্ত্রণে রেখে প্রতিটা জোড়া আলাদা কিনা বলে।
সমাধান ৮ (★★)¶
(ক) \(\mathrm{SSW}\) identity থেকে: $\(\mathrm{SSW}=\mathrm{SST}-\mathrm{SSB}=7299.15-2674.99=\mathbf{4624.16}\approx 4624.2.\ \checkmark\)$ (\(\mathrm{SST}=\mathrm{SSB}+\mathrm{SSW}\) — সমাধান ১১-এ প্রমাণিত।)
(খ) effect size \(\eta^2\): $\(\eta^2=\frac{\mathrm{SSB}}{\mathrm{SST}}=\frac{2674.99}{7299.15}=\mathbf{0.366}.\)$ অর্থাৎ একা fertilizer total ফলন-variation-এর \(\approx 37\%\) ব্যাখ্যা করে। এটি regression-এর \(R^2\)-এর সঙ্গে অভিন্ন — dummy-encoded regression-এ \(R^2\) ঠিক \(0.366\) আসবে।
(গ) residual-পতনের ব্যাখ্যা। one-way model irrigation-কে উপেক্ষা করে, তাই irrigation-এর সৃষ্ট ফলন-পার্থক্য (high গড়ে \(+6\)) "residual/within" bucket-এ গিয়ে জমে — \(\mathrm{SSW}=4624.2\) ফুলে থাকে। two-way model irrigation-কে আলাদা term করায় তার variation (\(\mathrm{SS}_{\text{irrig}}=2714.4\) + interaction \(111.7\)) residual থেকে বেরিয়ে যায়, residual নামে \(1798.0\)-এ। ফলে \(\mathrm{MSW}\) ছোট হয়:
$\(\mathrm{MSW}_{\text{1-way}}=\frac{4624.2}{117}=39.52\ \longrightarrow\ \mathrm{MS}_{\text{resid, 2-way}}=\frac{1798.0}{114}=15.77.\)$
\(F=\mathrm{MSB}/\mathrm{MSW}\)-তে denominator ছোট হওয়ায় একই \(\mathrm{SSB}_{\text{fert}}=2674.99\)-তে \(F\) বড়: \(\frac{1337.5}{39.52}=33.84\to\frac{1337.5}{15.77}=84.80\)। এ-ই blocking-এর power — nuisance-উৎস (এখানে irrigation) model-এ আনলে noise কমে, একই signal আরও পরিষ্কার দেখা যায়।
সমাধান ৯ (★★)¶
(ক) mean-পার্থক্য থেকে সরাসরি যাচাই: $\(\bar y_B-\bar y_A=38.10-32.40=\mathbf{5.70},\quad \bar y_C-\bar y_A=43.97-32.40=\mathbf{11.57},\quad \bar y_C-\bar y_B=43.97-38.10=\mathbf{5.87}.\)$ Tukey-র output (\(5.70,\ 11.56,\ 5.87\))-এর সাথে হুবহু মেলে (rounding-এ \(11.56\) vs \(11.57\))। অর্থাৎ Tukey-র point estimate কেবল group-গড়ের পার্থক্য; Tukey-র অবদান হলো এদের চারপাশে FWER-নিয়ন্ত্রিত confidence interval ও adjusted \(p\)।
(খ) Tukey-র CI চওড়া কেন, লাভ কী। সাধারণ two-sample-\(t\) একটিমাত্র জোড়ার জন্য critical value \(t_{\alpha/2}\) ব্যবহার করে। কিন্তু একসাথে তিন জোড়া দেখলে error জমে; Tukey তাই \(t\)-এর বদলে studentized range distribution-এর (বড়) critical value ব্যবহার করে, যা সব \(\binom{k}{2}\) জোড়া মিলিয়ে FWER-কে \(0.05\)-এ আটকায়। ফলে প্রতিটি interval একটু চওড়া — বিনিময়ে "অন্তত একটা মিথ্যা পার্থক্য" পাওয়ার ঝুঁকি \(5\%\)-এর বেশি হয় না (সমাধান ২-এর inflation এড়ানো)।
(গ) ক্রম। তিন জোড়ার CI-ই শূন্যকে বাদ দিয়েছে (সব reject), আর \(\bar y_A<\bar y_B<\bar y_C\), তাই দ্ব্যর্থহীন ক্রম \(\boxed{A<B<C}\) — যা ground-truth effect \(A{:}0<B{:}5<C{:}8\)-এর সাথে সম্পূর্ণ সঙ্গতিপূর্ণ।
সমাধান ১০ (★★)¶
\(k_1=3\) (fert), \(k_2=2\) (irrig), \(n=120\), cell \(=3\times2=6\)।
(ক) df: $\(df_{\text{fert}}=k_1-1=2,\quad df_{\text{irrig}}=k_2-1=1,\quad df_{\text{int}}=(k_1-1)(k_2-1)=2,\)$ $\(df_{\text{resid}}=n-k_1k_2=120-6=114,\quad df_{\text{total}}=n-1=119.\)$ যাচাই: \(2+1+2+114=119\) ✓।
(খ) MS ও F (denominator \(\mathrm{MS}_{\text{resid}}=1798.03/114=15.77\)):
| Source | \(\mathrm{SS}\) | \(df\) | \(\mathrm{MS}=\mathrm{SS}/df\) | \(F=\mathrm{MS}/15.77\) |
|---|---|---|---|---|
| fert | \(2674.99\) | \(2\) | \(1337.49\) | \(\mathbf{84.80}\) |
| irrig | \(2714.42\) | \(1\) | \(2714.42\) | \(\mathbf{172.10}\) |
| fert \(\times\) irrig | \(111.72\) | \(2\) | \(55.86\) | \(\mathbf{3.54}\) |
| Residual | \(1798.03\) | \(114\) | \(15.77\) | — |
| Total | \(\mathbf{7299.16}\) | \(119\) | — | — |
(গ) \(\mathrm{SST}\): \(2674.99+2714.42+111.72+1798.03=\mathbf{7299.16}\) — যা one-way-এর \(\mathrm{SST}=7299.15\)-এর সমান (rounding ছাড়া), কারণ total variation কোন model বেছেছি তার উপর নির্ভর করে না; শুধু তার বিভাজন বদলায়। তিনটা \(F\)-ই canonical-এর সাথে মিলেছে।
গ · প্রমাণভিত্তিক (proof-based)¶
সমাধান ১১ (★★) — \(\mathrm{SST}=\mathrm{SSB}+\mathrm{SSW}\)¶
প্রতিটি deviation-কে দুই টুকরো করি (group-গড় \(\bar y_g\) মাঝে বসিয়ে): $\(y_{gi}-\bar y=(y_{gi}-\bar y_g)+(\bar y_g-\bar y).\)$ দুপাশে বর্গ করে double-sum: $\(\mathrm{SST}=\sum_g\sum_i (y_{gi}-\bar y)^2=\sum_g\sum_i\Big[(y_{gi}-\bar y_g)^2+(\bar y_g-\bar y)^2+2(y_{gi}-\bar y_g)(\bar y_g-\bar y)\Big].\)$ তিনটা term আলাদা করি: - প্রথম: \(\sum_g\sum_i(y_{gi}-\bar y_g)^2=\mathrm{SSW}\)। - দ্বিতীয়: \((\bar y_g-\bar y)\) \(i\)-নিরপেক্ষ, তাই \(\sum_i\) দিলে \(n_g\) গুণ: \(\sum_g n_g(\bar y_g-\bar y)^2=\mathrm{SSB}\)। - cross-term: \(2\sum_g(\bar y_g-\bar y)\underbrace{\sum_i(y_{gi}-\bar y_g)}_{=\,0}\)। ভেতরের যোগফল শূন্য, কারণ group-গড়ের সংজ্ঞাই হলো \(\sum_i(y_{gi}-\bar y_g)=\sum_i y_{gi}-n_g\bar y_g=0\)।
তাই cross-term অদৃশ্য, আর $\(\boxed{\mathrm{SST}=\mathrm{SSB}+\mathrm{SSW}}.\qquad\blacksquare\)$ (গঠনগতভাবে এটি ৫.১-এর \(\mathrm{SST}=\mathrm{SSR}+\mathrm{SSE}\)-র হুবহু অনুরূপ; সেখানে projection-এর orthogonality, এখানে group-গড়ের zero-deviation cross-term-কে মারে।)
সমাধান ১২ (★★★) — \(\mathbb E[\mathrm{MSW}]=\sigma^2\)¶
Model: \(y_{gi}=\mu_g+\varepsilon_{gi}\), \(\varepsilon_{gi}\) iid mean-\(0\) variance-\(\sigma^2\)।
(ক) একটা group-এ \(\sum_i(y_{gi}-\bar y_g)^2\) হলো ঠিক \((n_g-1)\) গুণ sample variance-এর numerator। জানা ফল (sample variance-এর unbiasedness, ৪.১/৪.৪): \(\mathbb E\!\big[(n_g-1)s_g^2\big]=(n_g-1)\sigma^2\), অর্থাৎ $\(\mathbb E\Big[\sum_i(y_{gi}-\bar y_g)^2\Big]=(n_g-1)\sigma^2.\)$ (দ্রুত যাচাই: \(\sum_i(y_{gi}-\bar y_g)^2=\sum_i\varepsilon_{gi}^2-n_g\bar\varepsilon_g^2\); \(\mathbb E[\sum\varepsilon^2]=n_g\sigma^2\), \(\mathbb E[n_g\bar\varepsilon_g^2]=n_g\cdot\frac{\sigma^2}{n_g}=\sigma^2\); বিয়োগ \(=(n_g-1)\sigma^2\)।) লক্ষ করুন এতে \(\mu_g\) ঢোকেইনি — তাই group-গড় ভিন্ন হলেও এই প্রত্যাশা অপরিবর্তিত।
(খ) সব group-এর উপর যোগ: $\(\mathbb E[\mathrm{SSW}]=\sum_g(n_g-1)\sigma^2=\Big(\sum_g n_g-k\Big)\sigma^2=(n-k)\sigma^2,\)$ $\(\therefore\ \mathbb E[\mathrm{MSW}]=\mathbb E\!\left[\frac{\mathrm{SSW}}{n-k}\right]=\sigma^2.\)$ অর্থাৎ \(\mathrm{MSW}\) সর্বদা \(\sigma^2\)-এর unbiased estimator — \(H_0\) সত্য হোক বা না-হোক।
(গ) numerator-এর গল্প। \(\bar y_g=\mu_g+\bar\varepsilon_g\), grand \(\bar y=\bar\mu+\bar\varepsilon\)। \(\mathrm{SSB}=\sum_g n_g(\bar y_g-\bar y)^2\)-এ এটা ভাঙলে একটা deterministic signal-term \(\sum_g n_g(\mu_g-\bar\mu)^2\) আর একটা noise-term পাওয়া যায়; প্রত্যাশা নিলে $\(\mathbb E[\mathrm{MSB}]=\sigma^2+\frac{1}{k-1}\sum_g n_g(\mu_g-\bar\mu)^2\ \ge\ \sigma^2,\)$ সমতা ঠিক তখনই যখন সব \(\mu_g\) সমান (signal-term \(=0\))। উপসংহার: denominator (\(\mathrm{MSW}\)) সবসময় শুধু \(\sigma^2\); numerator (\(\mathrm{MSB}\)) সেই \(\sigma^2\) + group-পার্থক্যের signal। তাই \(H_0\)-তে \(\mathbb E[F]\approx1\) (\(F\to1\) যদি \(n\) বড়), আর \(H_0\) মিথ্যা হলে numerator ফুলে \(F\) বড় — এ-ই \(F\)-test-এর হৃৎপিণ্ড। \(\blacksquare\)
সমাধান ১৩ (★★★) — \(k=2\)-তে \(F=t^2\)¶
\(k=2\), group \(1,2\), size \(n_1,n_2\), \(n=n_1+n_2\), pooled \(s_p^2=\mathrm{MSW}=\frac{\mathrm{SSW}}{n-2}\)। \(df_B=1\) বলে $\(F=\frac{\mathrm{SSB}/1}{\mathrm{MSW}}=\frac{\mathrm{SSB}}{s_p^2}.\)$
\(\mathrm{SSB}\) সরল করি। grand mean \(\bar y=\frac{n_1\bar y_1+n_2\bar y_2}{n}\), তাই $\(\bar y_1-\bar y=\bar y_1-\frac{n_1\bar y_1+n_2\bar y_2}{n}=\frac{n_2(\bar y_1-\bar y_2)}{n},\qquad \bar y_2-\bar y=\frac{n_1(\bar y_2-\bar y_1)}{n}.\)$ এখন $\(\mathrm{SSB}=n_1(\bar y_1-\bar y)^2+n_2(\bar y_2-\bar y)^2=n_1\frac{n_2^2}{n^2}(\bar y_1-\bar y_2)^2+n_2\frac{n_1^2}{n^2}(\bar y_1-\bar y_2)^2\)$ $\(=\frac{n_1n_2(n_2+n_1)}{n^2}(\bar y_1-\bar y_2)^2=\frac{n_1n_2}{n}(\bar y_1-\bar y_2)^2=\frac{(\bar y_1-\bar y_2)^2}{\frac1{n_1}+\frac1{n_2}}.\)$ (শেষ ধাপে \(\frac{n_1n_2}{n_1+n_2}=\big(\frac1{n_1}+\frac1{n_2}\big)^{-1}\)।) তাই $\(F=\frac{\mathrm{SSB}}{s_p^2}=\frac{(\bar y_1-\bar y_2)^2}{s_p^2\left(\frac1{n_1}+\frac1{n_2}\right)}=\left[\frac{\bar y_1-\bar y_2}{s_p\sqrt{\frac1{n_1}+\frac1{n_2}}}\right]^2=t^2.\qquad\blacksquare\)$ distribution-পর্যায়েও সঙ্গতিপূর্ণ: \(t_{n-2}^2\overset{d}{=}F_{1,\,n-2}\) (একটা standard normal-এর বর্গ ভাগ chi-square = \(F_{1,\cdot}\))। তাই two-group ANOVA আর pooled two-sample \(t\)-test হুবহু একই test — ANOVA সত্যিই \(t\)-test-এর \(k>2\) সাধারণীকরণ (৪.৭-এর সাথে সরাসরি সংযোগ)।
ঘ · কোডিং (Python)¶
সমাধান ১৪ (★★★) — পূর্ণ ANOVA pipeline¶
নিচের একটিমাত্র runnable script ১-৪ সব ধাপ করে; প্রতিটি সংখ্যা canonical-এর সাথে মিলিয়ে assert দিয়ে যাচাই করা।
import numpy as np
import pandas as pd
from scipy import stats
import statsmodels.formula.api as smf
from statsmodels.stats.anova import anova_lm
from statsmodels.stats.multicomp import pairwise_tukeyhsd
# ---------- Dataset (seed 20260619, n=120) ----------
rng = np.random.default_rng(20260619)
fert = np.repeat(['A', 'B', 'C'], 40)
irrig = np.tile(np.repeat(['low', 'high'], 20), 3)
fe = {'A': 0.0, 'B': 5.0, 'C': 8.0}
ie = {'low': 0.0, 'high': 6.0}
mu = np.array([30.0 + fe[f] + ie[i] + (4.0 if (f == 'C' and i == 'high') else 0.0)
for f, i in zip(fert, irrig)])
crop = mu + rng.normal(0, 4, 120)
df = pd.DataFrame({'crop': crop, 'fert': fert, 'irrig': irrig})
# ========== STEP 1: from-scratch one-way ANOVA (crop ~ fert) ==========
groups = ['A', 'B', 'C']
n, k = len(df), 3
grand_mean = df['crop'].mean()
SSB = SSW = 0.0
means = {}
for g in groups:
v = df.loc[df['fert'] == g, 'crop'].values
m = v.mean(); means[g] = m
SSB += len(v) * (m - grand_mean) ** 2
SSW += ((v - m) ** 2).sum()
df_B, df_W = k - 1, n - k # 2, 117
MSB, MSW = SSB / df_B, SSW / df_W
F = MSB / MSW
p = stats.f.sf(F, df_B, df_W)
print("STEP 1 — from-scratch one-way ANOVA")
for g in groups:
print(f" mean_{g} = {means[g]:.4f}")
print(f" grand = {grand_mean:.4f}")
print(f" {'Source':<10}{'SS':>11}{'df':>5}{'MS':>11}{'F':>9}{'p':>13}")
print(f" {'Between':<10}{SSB:>11.2f}{df_B:>5}{MSB:>11.2f}{F:>9.2f}{p:>13.3e}")
print(f" {'Within':<10}{SSW:>11.2f}{df_W:>5}{MSW:>11.2f}")
print(f" {'Total':<10}{SSB+SSW:>11.2f}{n-1:>5}")
# ========== STEP 2: confirm with statsmodels ==========
m1 = smf.ols('crop ~ C(fert)', data=df).fit()
aov1 = anova_lm(m1, typ=2)
print("\nSTEP 2 — statsmodels confirmation")
print(aov1.round(4))
assert np.allclose([F, SSB, SSW],
[aov1.loc['C(fert)', 'F'],
aov1.loc['C(fert)', 'sum_sq'],
aov1.loc['Residual', 'sum_sq']])
print(" match: hand-computed == statsmodels ✓")
# ========== STEP 3: two-way ANOVA ==========
m2 = smf.ols('crop ~ C(fert)*C(irrig)', data=df).fit()
aov2 = anova_lm(m2, typ=2)
print("\nSTEP 3 — two-way ANOVA crop ~ C(fert)*C(irrig)")
print(aov2.round(4))
print("\n cell means (3x2):")
print(df.groupby(['fert', 'irrig'])['crop'].mean().round(2).unstack())
# ========== STEP 4: post-hoc Tukey HSD ==========
print("\nSTEP 4 — Tukey HSD on fert")
print(pairwise_tukeyhsd(df['crop'], df['fert'], alpha=0.05))
প্রত্যাশিত আউটপুট (সংক্ষেপে):
STEP 1 — from-scratch one-way ANOVA
mean_A = 32.4040
mean_B = 38.1029
mean_C = 43.9686
grand = 38.1585
Source SS df MS F p
Between 2674.99 2 1337.49 33.84 2.529e-12
Within 4624.17 117 39.52
Total 7299.15 119
STEP 2 — statsmodels confirmation
sum_sq df F PR(>F)
C(fert) 2674.9854 2.0 33.8410 0.0
Residual 4624.1689 117.0 NaN NaN
match: hand-computed == statsmodels ✓
STEP 3 — two-way ANOVA crop ~ C(fert)*C(irrig)
sum_sq df F PR(>F)
C(fert) 2674.9854 2.0 84.8008 0.0000
C(irrig) 2714.4226 1.0 172.1021 0.0000
C(fert):C(irrig) 111.7193 2.0 3.5417 0.0322
Residual 1798.0270 114.0 NaN NaN
cell means (3x2):
irrig high low
fert
A 36.26 28.55
B 42.43 33.78
C 50.06 37.88
STEP 4 — Tukey HSD on fert
Multiple Comparison of Means - Tukey HSD, FWER=0.05
group1 group2 meandiff p-adj lower upper reject
A B 5.6989 0.0003 2.3618 9.0361 True
A C 11.5646 0.0 8.2275 14.9017 True
B C 5.8657 0.0002 2.5285 9.2028 True
পাঠোদ্ধার।
- STEP 1 vs 2: hand-computed \(F=33.84\), \(\mathrm{SSB}=2674.99\), \(\mathrm{SSW}=4624.17\) — statsmodels-এর সাথে চার দশমিক পর্যন্ত হুবহু (assert np.allclose পাস), তাই ANOVA black box নয়; কেবল variance ভাগ করে অনুপাত নেওয়া।
- STEP 3: irrigation model-এ এনে residual \(4624\to1798\) নামল, তাই fert-এর \(F\) \(33.84\to84.80\) (denominator ছোট); irrigation-এর effect বিশাল (\(F=172.10\)); interaction ছোট কিন্তু significant (\(F=3.54,\ p=0.032\)) — cell-mean table-এ দৃশ্যমান যে \(C\)+high-এ বাড়তি লাফ (\(50.06\), additive প্রত্যাশার চেয়ে বেশি)।
- STEP 4: তিন জোড়াই reject (সব CI শূন্য বাদ দিয়েছে), ক্রম \(A<B<C\) — ground truth \(0<5<8\)-এর সাথে সঙ্গতিপূর্ণ।
typ=2নোট। balanced design (প্রতি cell সমান \(n\)) হলে Type I/II/III sum of squares মূলত একই ফল দেয়; তবু interaction-সহ model-এtyp=2(বাtyp=3) অভ্যাস হিসেবে নিরাপদ — এগুলো term-এর প্রবেশক্রম-নিরপেক্ষ।