@@ -774,7 +774,7 @@ void ModelSpecifics<BaseModel,RealType>::getSchoenfeldResidualsImpl(int index,
774774 IteratorType it (hX, index);
775775
776776 RealType resNumerator = static_cast <RealType>(0 );
777- RealType resDenominator = static_cast <RealType>(0 );
777+ // RealType resDenominator = static_cast<RealType>(0);
778778 RealType scoreNumerator1 = static_cast <RealType>(0 );
779779 RealType scoreNumerator2 = static_cast <RealType>(0 );
780780 RealType scoreDenominator = static_cast <RealType>(0 );
@@ -793,16 +793,10 @@ void ModelSpecifics<BaseModel,RealType>::getSchoenfeldResidualsImpl(int index,
793793
794794 auto processRow = [&](int i, RealType x) {
795795
796- // std::cerr << "row " << i << "\n";
797-
798- // std::cerr << "r" << *reset << " ";
799-
800- if (*reset <= i) {
801-
802- // std::cerr << *reset << " ";
796+ if (*reset <= hPid[i]) {
803797
804798 resNumerator = static_cast <RealType>(0 );
805- resDenominator = static_cast <RealType>(0 );
799+ // resDenominator = static_cast<RealType>(0);
806800 scoreNumerator1 = static_cast <RealType>(0 );
807801 scoreNumerator2 = static_cast <RealType>(0 );
808802 scoreDenominator = static_cast <RealType>(0 );
@@ -812,25 +806,27 @@ void ModelSpecifics<BaseModel,RealType>::getSchoenfeldResidualsImpl(int index,
812806
813807 const auto expXBeta = offsExpXBeta[i]; // std::exp(hXBeta[i]);
814808
815- resNumerator += expXBeta * x;
816- resDenominator += expXBeta;
809+ resNumerator += hKWeight[i] * expXBeta * x;
810+ // resDenominator += expXBeta;
817811
818812 if (hY[i] == 1 ) {
819813 // std::cerr << " " << x << " for " << resNumerator << " / " << resDenominator << " - " << ( x - resNumerator / resDenominator) << "\n";
820814 // std::cerr << denomPid[i] << "\n";
821815 if (hasResiduals) {
822- if (i < N && i < *reset &&
816+ if (i < (K - 1 ) && hPid[i] < *reset &&
823817 (hOffs[i] == hOffs[i+ 1 ]) && hY[i + 1 ] == 1 ) {
824818 deferredResidualX.push_back (x);
825819 } else {
826820
821+ const auto denom = accDenomPid[hPid[i]];
822+
827823 while (deferredResidualX.size () > 0 ) {
828- const auto residual = deferredResidualX.front () - resNumerator / resDenominator ;
824+ const auto residual = deferredResidualX.front () - resNumerator / denom ;
829825 residuals->push_back (residual);
830826 deferredResidualX.pop_front ();
831827 }
832828
833- const auto residual = x - resNumerator / resDenominator ;
829+ const auto residual = x - resNumerator / denom ;
834830 residuals->push_back (residual);
835831 }
836832 }
@@ -845,64 +841,21 @@ void ModelSpecifics<BaseModel,RealType>::getSchoenfeldResidualsImpl(int index,
845841 }
846842
847843 if (hasScore) {
848-
849- // std::cerr << "i = " << i << "\n";
850- const auto weight = covariate[i];
851- // MAS does not believe reweighing is correct, but is matching cox.zph
852-
853- // const auto xt = x * covariate[i];
854- // MAS believes covariate should be adjusted
855- const auto numerator1 = expXBeta * x; // TODO not xt?
856- const auto numerator2 = expXBeta * x * x; // TODO not xt?
844+ const auto cov = covariate[i];
845+ const auto numerator1 = hKWeight[i] * expXBeta * x;
846+ const auto numerator2 = hKWeight[i] * expXBeta * x * x;
857847
858848 if (hY[i] == 1 ) {
859- uGradient2 += x;
860- wGradient2 += x * weight; // TODO not xt and no weight?
849+ uGradient2 += hKWeight[i] * x;
850+ wGradient2 += hKWeight[i] * x * cov;
861851 }
862852
863853 scoreNumerator1 += numerator1;
864854 scoreNumerator2 += numerator2;
865855
866- // if (hY[i] == 1) {
867-
868- if (hY[i] == 1 && i < (K - 1 ) && i < *reset &&
869- (hOffs[i] == hOffs[i+ 1 ]) && hY[i + 1 ] == 1 ) {
870-
871- // deferredScore1.push_back(scoreNumerator1);
872- // deferredScore2.push_back(scoreNumerator2);
873- // // deferredScore3.push_back(hNWeight[hPid[i]]);
874- // deferredScore3.push_back(0.0);
875- // deferredScore4.push_back(i);
876-
877- } else {
878-
879- // while (deferredScore1.size() > 0) {
880- //
881- // const auto popScoreNumerator1 = deferredScore1.front();
882- // const auto popScoreNumerator2 = deferredScore2.front();
883- // const auto popNWeight = deferredScore3.front();
884- // const auto popI = deferredScore4.front();
885- //
886- // const auto denom = accDenomPid[hPid[popI]];
887- //
888- // const auto t = scoreNumerator1 / denom;
889- // const auto gradient = popNWeight * t;
890- // const auto hessian = popNWeight * (scoreNumerator2 / denom - t * t);
891- //
892- // uGradient += gradient;
893- // wGradient += gradient * weight;
894- //
895- // // std::cerr<< "newP" << popI << " " << hPid[popI] << " " << scoreNumerator1 << "/" << denom << " " << hY[popI] << " " << uGradient << " " << popNWeight << "\n";
896- //
897- // uHessian += hessian;
898- // wHessian += hessian * weight * weight;
899- // xHessian += hessian * weight;
900- //
901- // deferredScore1.pop_front();
902- // deferredScore2.pop_front();
903- // deferredScore3.pop_front();
904- // deferredScore4.pop_front();
905- // }
856+ if (i < (K - 1 ) && hPid[i] == hPid[i + 1 ]) {
857+ // zero contribution under Breslow
858+ } else {
906859
907860 const auto denom = accDenomPid[hPid[i]];
908861
@@ -911,22 +864,19 @@ void ModelSpecifics<BaseModel,RealType>::getSchoenfeldResidualsImpl(int index,
911864 const auto hessian = hNWeight[hPid[i]] * (scoreNumerator2 / denom - t * t);
912865
913866 uGradient += gradient;
914- wGradient += gradient * weight ;
867+ wGradient += gradient * cov ;
915868
916- // std::cerr<< "newA" << i << " " << hPid[i] << " " << scoreNumerator1 << "/" << denom << " " << hY[i] << " " << uGradient << " " << hNWeight[hPid[i]] << "\n";
869+ // std::cerr << "newA" << i << " " << hPid[i] << " " << scoreNumerator1 << "/" << denom << " " << hY[i] << " " << uGradient << " " << hNWeight[hPid[i]] << "\n";
917870
918871 uHessian += hessian;
919- wHessian += hessian * weight * weight ;
920- xHessian += hessian * weight ;
872+ wHessian += hessian * cov * cov ;
873+ xHessian += hessian * cov ;
921874 }
922875 }
923876 };
924877
925878 // main loop
926-
927- // for (int i = 0; i <= N; ++i) {
928879 for (int i = 0 ; i < K; ++i) {
929- // std::cerr << i << " ";
930880 if (i == it.index ()) {
931881 processRow (i, it.value ());
932882 ++it;
@@ -1183,6 +1133,9 @@ void ModelSpecifics<BaseModel,RealType>::computeGradientAndHessianImpl(int index
11831133 w, // Signature-only, for iterator-type specialization
11841134 &gradient, &hessian, accNumerPid, accNumerPid2,
11851135 accDenomPid[i], hNWeight[i], 0.0 , hXBeta[i], hY[i]); // When function is in-lined, compiler will only use necessary arguments
1136+
1137+ // std::cerr << "oldA" << i << " " << accNumerPid << "/" << accDenomPid[i] << " " << hY[i] << " " << gradient << " " << hNWeight[i] << "\n";
1138+
11861139 ++it;
11871140
11881141 if (IteratorType::isSparse) {
@@ -1201,6 +1154,8 @@ void ModelSpecifics<BaseModel,RealType>::computeGradientAndHessianImpl(int index
12011154 w, // Signature-only, for iterator-type specialization
12021155 &gradient, &hessian, accNumerPid, accNumerPid2,
12031156 accDenomPid[i], hNWeight[i], static_cast <RealType>(0 ), hXBeta[i], hY[i]); // When function is in-lined, compiler will only use necessary arguments
1157+
1158+ // std::cerr << "oldB" << i << " " << accNumerPid << "/" << accDenomPid[i] << " " << hY[i] << " " << gradient << " " << hNWeight[i] << "\n";
12041159 }
12051160 }
12061161 }
@@ -2312,7 +2267,7 @@ void ModelSpecifics<BaseModel,RealType>::setPidForAccumulationImpl(const AnyReal
23122267
23132268 if (nextPid != lastPid) { // start new strata
23142269 pid++;
2315- accReset.push_back (pid + nTies );
2270+ accReset.push_back (pid);
23162271 nTies = 0 ;
23172272 lastPid = nextPid;
23182273 } else {
@@ -2333,7 +2288,7 @@ void ModelSpecifics<BaseModel,RealType>::setPidForAccumulationImpl(const AnyReal
23332288 }
23342289 }
23352290 pid++;
2336- accReset.push_back (pid + nTies); // TODO BUG HERE????
2291+ accReset.push_back (pid);
23372292
23382293 // Save number of denominators
23392294 N = pid;
0 commit comments