00001 using System;
00002 using System.Collections.Generic;
00003 using System.Linq;
00004 using System.Text;
00005
00006 namespace StephenAshley.Biostatistics
00007 {
00008 using NUMBER = Decimal;
00016 public class WilcoxonGroupsCollection : GroupsCollection
00017 {
00021 public WilcoxonGroupsCollection() : base() { }
00022
00028 public WilcoxonGroupsCollection(List<Group> groups)
00029 : base(groups)
00030 {
00031 if (groups.Count > 2)
00032 throw new BiostatisticsException(
00033 "WilcoxonGroupsCollection has more than two Groups.");
00034 }
00035
00046 public override void Add(Group group)
00047 {
00048 if (group == null)
00049 throw new BiostatisticsException(
00050 "group is a null reference.");
00051
00052 if (groupsArray == null || k() == 0)
00053 {
00054 base.Add(group);
00055 return;
00056 }
00057
00058 if (k() == 1 && group.n() == groupsArray[0].n())
00059 {
00060 base.Add(group);
00061 List<Rank> lstRanks = new List<Rank>();
00062
00063
00064
00065 for (Int32 i = 0; i < group.n(); i++)
00066 {
00067 if (groupsArray[0][i] - groupsArray[1][i] != 0.0m)
00068 lstRanks.Add(new Rank(0, groupsArray[0][i]
00069 - groupsArray[1][i], 0.0m));
00070 }
00071 iN = lstRanks.Count;
00072
00073
00074 lstRanks.Sort(Rank.CompareRanksByAbsoluteValues);
00075
00076
00077 for (Int32 i = 0; i < lstRanks.Count; i++)
00078 lstRanks[i] = new Rank(lstRanks[i].iGroup, lstRanks[i].decValue,
00079 (NUMBER)(i + 1));
00080
00081
00082 iTieAdjustment = Rank.AdjustTies(ref lstRanks);
00083
00084
00085 for (Int32 i = 0; i < lstRanks.Count; i++)
00086 {
00087 if (lstRanks[i].decValue < 0)
00088 lstRanks[i] = new Rank(lstRanks[i].iGroup, lstRanks[i].decValue,
00089 -1.0m * lstRanks[i].decRank);
00090 }
00091
00092 decW = 0.0m;
00093 decTminus = 0.0m;
00094 decTplus = 0.0m;
00095
00096 foreach (Rank rank in lstRanks)
00097 {
00098 NUMBER rnk = rank.decRank;
00099 NUMBER val = rank.decValue;
00100
00101 if (val > 0.0m)
00102 decTplus += rnk;
00103 else
00104 decTminus += -1.0m * rnk;
00105
00106 decW += rnk;
00107 }
00108 decW = DecMath.Abs(decW);
00109
00110
00111
00112 NUMBER decA = n() * (n() + 1) * (2 * n() + 1);
00113 NUMBER decB = decA / 6.0m;
00114 NUMBER decC = ((NUMBER)iTieAdjustment) / 12.0m;
00115 NUMBER decD = decB - decC;
00116 decStandardDeviationW = DecMath.Sqrt(decD);
00117
00118 NUMBER decE = ((NUMBER)iTieAdjustment) / 2.0m;
00119 NUMBER decF = (decA - decE) / 24.0m;
00120 decStandardDeviationT = DecMath.Sqrt(decF);
00121
00122 return;
00123 }
00124
00125 if (k() == 1 && group.n() != groupsArray[0].n())
00126 {
00127 throw new BiostatisticsException(
00128 "WilcoxonGroupsCollection Groups must have equal sizes.");
00129 }
00130
00131 if (k() > 1)
00132 {
00133 throw new BiostatisticsException(
00134 "Addition of Group to WilcoxonGroupsCollection that contains more than 1 Group.");
00135 }
00136 }
00137
00150 public NUMBER CriticalValue()
00151 {
00152 NUMBER decT;
00153
00154 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00155 throw new BiostatisticsException(
00156 "groupsArray not complete.");
00157
00158 if (n() < 4 || n() > 100)
00159 throw new BiostatisticsException(
00160 "n() outside the range of the critical values table.");
00161
00162 if (decTplus < decTminus)
00163 decT = decTplus;
00164 else
00165 decT = decTminus;
00166
00167 if (CriticalValues[n() - 4, 1] < decT)
00168 throw new BiostatisticsException(
00169 "p > 0.5");
00170
00171 if (CriticalValues[n() - 4, 1] == decT)
00172 return 0.5m;
00173
00174 Int16 iLastColumn = 3;
00175 for (; iLastColumn < 9; iLastColumn++)
00176 if (CriticalValues[n() - 4, iLastColumn] == null)
00177 break;
00178
00179
00180
00181
00182 for (Int16 i = (Int16)(iLastColumn - 1); i > 0; i--)
00183 if (decT <= CriticalValues[n() - 4, i])
00184 return alphas[i];
00185
00186 throw new BiostatisticsException(
00187 "Error in computation of critical value.");
00188 }
00189
00198 public NUMBER MuT()
00199 {
00200 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00201 throw new BiostatisticsException(
00202 "groupsArray not complete.");
00203
00204 return (n() * (n() + 1)) / 4.0m;
00205 }
00206
00216 public Int32 n()
00217 {
00218 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00219 throw new BiostatisticsException(
00220 "groupsArray not complete.");
00221
00222 return iN;
00223 }
00224
00234 public NUMBER p()
00235 {
00236 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00237 throw new BiostatisticsException(
00238 "groupsArray not complete.");
00239
00240 return Distributions.ProbabilityZ(Zw());
00241 }
00242
00252 public NUMBER pUncorrected()
00253 {
00254 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00255 throw new BiostatisticsException(
00256 "groupsArray not complete.");
00257
00258 return Distributions.ProbabilityZ(ZwUncorrected());
00259 }
00260
00269 public NUMBER StandardDeviationW()
00270 {
00271 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00272 throw new BiostatisticsException(
00273 "groupsArray not complete.");
00274
00275 return decStandardDeviationW;
00276 }
00277
00286 public NUMBER StandardDeviationT()
00287 {
00288 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00289 throw new BiostatisticsException(
00290 "groupsArray not complete.");
00291
00292 return decStandardDeviationT;
00293 }
00294
00303 public NUMBER Tminus()
00304 {
00305 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00306 throw new BiostatisticsException(
00307 "groupsArray not complete.");
00308
00309 return decTminus;
00310 }
00311
00320 public NUMBER Tplus()
00321 {
00322 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00323 throw new BiostatisticsException(
00324 "groupsArray not complete.");
00325
00326 return decTplus;
00327 }
00328
00337 public Int32 W()
00338 {
00339 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00340 throw new BiostatisticsException(
00341 "groupsArray not complete.");
00342
00343 return Convert.ToInt32(decW);
00344 }
00345
00354 public NUMBER Zt()
00355 {
00356 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00357 throw new BiostatisticsException(
00358 "groupsArray not complete.");
00359
00360 NUMBER decA = DecMath.Abs(Tplus() - MuT());
00361 NUMBER decZt;
00362
00363 try
00364 {
00365 decZt = (decA - 0.5m) / StandardDeviationT();
00366 }
00367 catch (Exception e)
00368 {
00369 throw new BiostatisticsException(e.Source + ": " + e.Message, e);
00370 }
00371 return decZt;
00372 }
00373
00382 public NUMBER ZtUncorrected()
00383 {
00384 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00385 throw new BiostatisticsException(
00386 "groupsArray not complete.");
00387
00388 NUMBER decA = DecMath.Abs(Tplus() - MuT());
00389 NUMBER decZt;
00390
00391 try
00392 {
00393 decZt = decA / StandardDeviationT();
00394 }
00395 catch (Exception e)
00396 {
00397 throw new BiostatisticsException(e.Source + ": " + e.Message, e);
00398 }
00399 return decZt;
00400 }
00401
00410 public NUMBER Zw()
00411 {
00412 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00413 throw new BiostatisticsException(
00414 "groupsArray not complete.");
00415
00416 NUMBER decA = DecMath.Abs(W()) - 0.5m;
00417 NUMBER decB = (NUMBER)(n() * (n() + 1) * (2 * n() + 1)) / 6.0m;
00418 NUMBER decC = DecMath.Sqrt(decB);
00419 NUMBER decZw;
00420 try
00421 {
00422 decZw = decA / decC;
00423 }
00424 catch (Exception e)
00425 {
00426 throw new BiostatisticsException(e.Source + ": " + e.Message, e);
00427 }
00428 return decZw;
00429 }
00430
00439 public NUMBER ZwUncorrected()
00440 {
00441 if (groupsArray == null || groupsArray[0] == null || groupsArray[1] == null)
00442 throw new BiostatisticsException(
00443 "groupsArray not complete.");
00444
00445 NUMBER decA = DecMath.Abs(W());
00446 NUMBER decB = (NUMBER)(n() * (n() + 1) * (2 * n() + 1)) / 6.0m;
00447 NUMBER decC = DecMath.Sqrt(decB);
00448 NUMBER decZw;
00449 try
00450 {
00451 decZw = decA / decC;
00452 }
00453 catch (Exception e)
00454 {
00455 throw new BiostatisticsException(e.Source + ": " + e.Message, e);
00456 }
00457 return decZw;
00458 }
00459
00460 private NUMBER decW;
00461 private NUMBER decTplus;
00462 private NUMBER decTminus;
00463 private Int32 iTieAdjustment;
00464 private NUMBER decStandardDeviationW;
00465 private NUMBER decStandardDeviationT;
00466 private Int32 iN;
00467
00468 private readonly NUMBER[] alphas =
00469 {
00470 0.0m, 0.5m, 0.2m, 0.1m, 0.05m, 0.02m, 0.01m, 0.005m, 0.001m
00471 };
00472
00473 private readonly Int16?[,] CriticalValues =
00474 {
00475 {4, 2, 0, null, null, null, null, null, null},
00476 {5, 4, 2, 0, null, null, null, null, null},
00477 {6, 6, 3, 2, 0, null, null, null, null},
00478 {7, 9, 5, 3, 2, 0, null, null, null},
00479 {8, 12, 8, 5, 3, 1, 0, null, null},
00480 {9, 16, 10, 8, 5, 3, 1, 0, null},
00481 {10, 20, 14, 10, 8, 5, 3, 1, null},
00482 {11, 24, 17, 13, 10, 7, 5, 3, 0},
00483 {12, 29, 21, 17, 13, 9, 7, 5, 1},
00484 {13, 35, 26, 21, 17, 12, 9, 7, 2},
00485 {14, 40, 31, 25, 21, 15, 12, 9, 4},
00486 {15, 47, 36, 30, 25, 19, 15, 12, 6},
00487 {16, 54, 42, 35, 29, 23, 19, 15, 8},
00488 {17, 61, 48, 41, 34, 27, 23, 19, 11},
00489 {18, 69, 55, 47, 40, 32, 27, 23, 14},
00490 {19, 77, 62, 53, 46, 37, 32, 27, 18},
00491 {20, 86, 69, 60, 52, 43, 37, 32, 21},
00492 {21, 95, 77, 67, 58, 49, 42, 37, 25},
00493 {22, 104, 86, 75, 65, 55, 48, 42, 30},
00494 {23, 114, 94, 83, 73, 62, 54, 48, 35},
00495 {24, 125, 104, 91, 81, 69, 61, 54, 40},
00496 {25, 136, 113, 100, 89, 76, 68, 60, 45},
00497 {26, 148, 124, 110, 98, 84, 75, 67, 51},
00498 {27, 160, 134, 119, 107, 92, 83, 74, 57},
00499 {28, 172, 145, 130, 116, 101, 91, 82, 64},
00500 {29, 185, 157, 140, 126, 110, 100, 90, 71},
00501 {30, 198, 169, 151, 137, 120, 109, 98, 78},
00502 {31, 212, 181, 163, 147, 130, 118, 107, 86},
00503 {32, 226, 194, 175, 159, 140, 128, 116, 94},
00504 {33, 241, 207, 187, 170, 151, 138, 126, 102},
00505 {34, 257, 221, 200, 182, 162, 148, 136, 111},
00506 {35, 272, 235, 213, 195, 173, 159, 146, 120},
00507 {36, 289, 250, 227, 208, 185, 171, 157, 130},
00508 {37, 305, 265, 241, 221, 198, 182, 168, 140},
00509 {38, 323, 281, 256, 235, 211, 194, 180, 150},
00510 {39, 340, 297, 271, 249, 224, 207, 192, 161},
00511 {40, 358, 313, 286, 264, 238, 220, 204, 172},
00512 {41, 377, 330, 302, 279, 252, 233, 217, 183},
00513 {42, 396, 348, 319, 294, 266, 247, 230, 195},
00514 {43, 416, 365, 336, 310, 281, 261, 244, 207},
00515 {44, 436, 384, 353, 327, 296, 276, 258, 220},
00516 {45, 456, 402, 371, 343, 312, 291, 272, 233},
00517 {46, 477, 422, 389, 361, 328, 307, 287, 246},
00518 {47, 499, 441, 407, 378, 345, 322, 302, 260},
00519 {48, 521, 462, 426, 396, 362, 339, 318, 274},
00520 {49, 543, 482, 446, 415, 379, 355, 334, 289},
00521 {50, 566, 503, 466, 434, 397, 373, 350, 304},
00522 {51, 590, 525, 486, 453, 416, 390, 367, 319},
00523 {52, 613, 547, 507, 473, 434, 408, 384, 335},
00524 {53, 638, 569, 529, 494, 454, 427, 402, 351},
00525 {54, 668, 592, 550, 514, 473, 445, 420, 368},
00526 {55, 688, 615, 573, 536, 493, 465, 438, 385},
00527 {56, 714, 639, 595, 557, 514, 484, 457, 402},
00528 {57, 740, 664, 618, 579, 535, 504, 477, 420},
00529 {58, 767, 688, 642, 602, 556, 525, 497, 438},
00530 {59, 794, 714, 666, 625, 578, 546, 517, 457},
00531 {60, 822, 739, 690, 648, 600, 567, 537, 476},
00532 {61, 850, 765, 715, 672, 623, 589, 558, 495},
00533 {62, 879, 792, 741, 697, 646, 611, 580, 515},
00534 {63, 908, 819, 767, 721, 669, 634, 602, 535},
00535 {64, 938, 847, 793, 747, 693, 657, 624, 556},
00536 {65, 968, 875, 820, 772, 718, 681, 647, 577},
00537 {66, 998, 903, 847, 798, 742, 705, 670, 599},
00538 {67, 1029, 932, 875, 825, 768, 729, 694, 621},
00539 {68, 1061, 962, 903, 852, 793, 754, 718, 643},
00540 {69, 1093, 992, 931, 879, 819, 779, 742, 666},
00541 {70, 1126, 1022, 960, 907, 846, 805, 767, 689},
00542 {71, 1159, 1053, 990, 936, 873, 831, 792, 712},
00543 {72, 1192, 1084, 1020, 964, 901, 858, 818, 736},
00544 {73, 1226, 1116, 1050, 994, 928, 884, 844, 761},
00545 {74, 1261, 1148, 1081, 1023, 957, 912, 871, 786},
00546 {75, 1296, 1181, 1112, 1053, 986, 940, 898, 811},
00547 {76, 1331, 1214, 1144, 1084, 1015, 968, 925, 836},
00548 {77, 1367, 1247, 1176, 1115, 1044, 997, 953, 862},
00549 {78, 1403, 1282, 1209, 1147, 1075, 1026, 980, 889},
00550 {79, 1440, 1316, 1242, 1179, 1105, 1056, 1010, 916},
00551 {80, 1478, 1351, 1276, 1211, 1136, 1086, 1039, 943},
00552 {81, 1516, 1387, 1310, 1244, 1168, 1116, 1036, 971},
00553 {82, 1554, 1423, 1345, 1277, 1200, 1147, 1099, 999},
00554 {83, 1593, 1459, 1380, 1311, 1232, 1178, 1129, 1028},
00555 {84, 1632, 1496, 1415, 1345, 1265, 1210, 1160, 1057},
00556 {85, 1672, 1533, 1451, 1380, 1298, 1242, 1191, 1086},
00557 {86, 1712, 1571, 1487, 1415, 1332, 1275, 1223, 1116},
00558 {87, 1753, 1609, 1524, 1451, 1366, 1308, 1255, 1146},
00559 {88, 1794, 1648, 1561, 1487, 1400, 1342, 1288, 1177},
00560 {89, 1836, 1688, 1599, 1523, 1435, 1376, 1321, 1208},
00561 {90, 1878, 1727, 1638, 1560, 1471, 1410, 1355, 1240},
00562 {91, 1921, 1767, 1676, 1597, 1507, 1445, 1389, 1271},
00563 {92, 1964, 1808, 1715, 1635, 1543, 1480, 1423, 1304},
00564 {93, 2008, 1849, 1755, 1674, 1580, 1516, 1458, 1337},
00565 {94, 2052, 1891, 1795, 1712, 1617, 1552, 1493, 1370},
00566 {95, 2097, 1933, 1836, 1752, 1655, 1589, 1529, 1404},
00567 {96, 2142, 1976, 1877, 1791, 1693, 1626, 1565, 1438},
00568 {97, 2187, 2019, 1918, 1832, 1731, 1664, 1601, 1472},
00569 {98, 2233, 2062, 1960, 1872, 1770, 1702, 1638, 1507},
00570 {99, 2280, 2106, 2003, 1913, 1810, 1740, 1676, 1543},
00571 {100, 2327, 2151, 2045, 1955, 1850, 1779, 1714, 1578}
00572 };
00573 }
00574 }