Browse code

First compiling version. Density is now gaussian normal.

chakalakka authored on 05/05/2014 15:05:06
Showing 10 changed files

... ...
@@ -5,3 +5,4 @@
5 5
 *.swp
6 6
 *.swo
7 7
 *~
8
+*_
... ...
@@ -1,6 +1,6 @@
1
-Package: anafinder
1
+Package: aneufinder
2 2
 Type: Package
3
-Title: Anaploidy analysis of Seq-data using a Hidden Markov Model
3
+Title: Aneuploidy analysis of Seq-data using a Hidden Markov Model
4 4
 Version: 0.1
5 5
 Date: 2014-05-01
6 6
 Author: Aaron Taudt, David Porubsky
... ...
@@ -1,11 +1,11 @@
1
-useDynLib(chromstar)
1
+useDynLib(aneufinder)
2 2
 
3 3
 # Export all names
4 4
 # exportPattern(".")
5 5
 export(
6 6
 bed2bin,
7 7
 bam2bin,
8
-bedGraph2bin,
8
+bedGraph2bin
9 9
 )
10 10
 
11 11
 # Import all packages listed as Imports or Depends
... ...
@@ -1,16 +1,14 @@
1
-#include "loghmm.h"
2 1
 #include "scalehmm.h"
3 2
 
4
-
5 3
 // ---------------------------------------------------------------
6 4
 // void R_univariate_hmm()
7 5
 // This function takes parameters from R, creates a univariate HMM object, creates the distributions, runs the Baum-Welch and returns the result to R.
8 6
 // ---------------------------------------------------------------
9 7
 extern "C" {
10
-void R_univariate_hmm(int* O, int* T, int* N, int* densityNames, double* r, double* p, int* maxiter, int* maxtime, double* eps, double* post, double* A, double* proba, double* loglik, double* softweights, double* initial_r, double* initial_p, double* initial_A, double* initial_proba, bool* use_initial_params, int* num_threads) {
8
+void R_univariate_hmm(int* O, int* T, int* N, double* means, double* variances, int* maxiter, int* maxtime, double* eps, double* post, double* A, double* proba, double* loglik, double* weights, double* initial_means, double* initial_variances, double* initial_A, double* initial_proba, bool* use_initial_params, int* num_threads) {
11 9
 
12 10
 	// Define logging level
13
-// 	FILE* pFile = fopen("chromStar.log", "w");
11
+// 	FILE* pFile = fopen("aneufinder.log", "w");
14 12
 // 	Output2FILE::Stream() = pFile;
15 13
 //  	FILELog::ReportingLevel() = FILELog::FromString("INFO");
16 14
  	FILELog::ReportingLevel() = FILELog::FromString("ITERATION");
... ...
@@ -42,11 +40,10 @@ void R_univariate_hmm(int* O, int* T, int* N, int* densityNames, double* r, doub
42 40
 
43 41
 	// Create the HMM
44 42
 	FILE_LOG(logDEBUG1) << "Creating a univariate HMM";
45
-// 	LogHMM* model = new LogHMM(*T, *N);
46
-	ScaleHMM* model = new ScaleHMM(*T, *N);
43
+	ScaleHMM* hmm = new ScaleHMM(*T, *N);
47 44
 	// Initialize the transition probabilities and proba
48
-	model->initialize_transition_probs(initial_A, *use_initial_params);
49
-	model->initialize_proba(initial_proba, *use_initial_params);
45
+	hmm->initialize_transition_probs(initial_A, *use_initial_params);
46
+	hmm->initialize_proba(initial_proba, *use_initial_params);
50 47
     
51 48
 	// Calculate mean and variance of data
52 49
 	double mean = 0, variance = 0;
... ...
@@ -62,386 +59,70 @@ void R_univariate_hmm(int* O, int* T, int* N, int* densityNames, double* r, doub
62 59
 	variance = variance / *T;
63 60
 	FILE_LOG(logINFO) << "data mean = " << mean << ", data variance = " << variance;		
64 61
 	
65
-	// Go through all states of the model and assign the density functions
62
+	// Go through all states of the hmm and assign the density functions
66 63
 	srand (clock());
67 64
 	int rand1, rand2;
68 65
 	double imean, ivariance;
69
-	//int i_count = 0;
70
-	for (int i_state=0; i_state<model->N; i_state++)
66
+	for (int istate=0; istate<*N; istate++)
71 67
 	{
72 68
 
73 69
 		if (*use_initial_params) {
74
-			FILE_LOG(logINFO) << "Using given parameters for r and p";
75
-			imean = (1-initial_p[i_state])*initial_r[i_state] / initial_p[i_state];
76
-			ivariance = imean / initial_p[i_state];
70
+			FILE_LOG(logINFO) << "Using given parameters for mean and variance";
71
+// 			TODO
77 72
 			FILE_LOG(logDEBUG3) << "imean = " << imean;
78 73
 			FILE_LOG(logDEBUG3) << "ivariance = " << ivariance;
79 74
 		} else {
80
-
81
-// 			// Disturb mean and variance for use as randomized initial parameters
82
-// 			FILE_LOG(logINFO) << "Using random initialization for r and p";
83
-// 			rand1 = rand();
84
-// 			rand2 = rand();
85
-// 			imean = (double)rand1/(double)RAND_MAX * 10*mean;
86
-// // 			ivariance = imean + (double)rand2/(double)RAND_MAX * 10*variance; // variance has to be greater than mean, otherwise r will be negative
87
-// 			ivariance = imean + (double)rand2/(double)RAND_MAX * 20*imean; // variance has to be greater than mean, otherwise r will be negative
88
-// 			FILE_LOG(logDEBUG3) << "RAND_MAX = " << RAND_MAX;
89
-// 			FILE_LOG(logDEBUG3) << "rand1 = " << rand1;
90
-// 			FILE_LOG(logDEBUG3) << "rand2 = " << rand2;
91
-// 			FILE_LOG(logDEBUG3) << "imean = " << imean;
92
-// 			FILE_LOG(logDEBUG3) << "ivariance = " << ivariance;
93
-
94
-// 	 		// Empirical initialization
95
-// 	 		if (i_state == 1) {
96
-// 				FILE_LOG(logINFO) << "Initializing r and p empirically for state 1";
97
-// 	 			imean = mean/2;
98
-// 	 			ivariance = imean*2;
99
-// 	 		} else if (i_state == 2) {
100
-// 				FILE_LOG(logINFO) << "Initializing r and p empirically for state 2";
101
-// 	 			imean = mean*2;
102
-// 	 			ivariance = imean*2;
103
-// 	 		} 
104
-
105
-			// Simple initialization, seems to give the fastest convergence
106
-	 		if (i_state == 1) {
107
-				FILE_LOG(logINFO) << "Initializing r and p for state 1";
108
-	 			imean = mean;
109
-	 			ivariance = variance;
110
-	 		} else if (i_state == 2) {
111
-				FILE_LOG(logINFO) << "Initializing r and p for state 2";
112
-	 			imean = mean+1;
113
-	 			ivariance = variance;
114
-	 		} 
115
-			
116
-			// Calculate r and p from mean and variance
117
-			initial_r[i_state] = pow(imean,2)/(ivariance-imean);
118
-			initial_p[i_state] = imean/ivariance;
75
+			// Simple initialization
76
+			imean = mean * pow(2, istate-1);
77
+			ivariance = variance * pow(2, istate-1);
119 78
 		}
120 79
 
121
-		if (densityNames[i_state] == NB)
122
-		{
123
-			FILE_LOG(logDEBUG1) << "Using negative binomial for state " << i_state;
124
-			NegativeBinomial *d = new NegativeBinomial(O, model->T, initial_r[i_state], initial_p[i_state]); // delete is done inside ~LogHMM()
125
-			model->densityFunctions.push_back(d);
126
-		}
127
-		else if (densityNames[i_state] == ZI)
128
-		{
129
-			FILE_LOG(logDEBUG1) << "Using only zeros for state " << i_state;
130
-			OnlyZeros *d = new OnlyZeros(O, model->T); // delete is done inside ~LogHMM()
131
-			model->densityFunctions.push_back(d);
132
-		}
133
-		else
134
-		{
135
-			FILE_LOG(logWARNING) << "Density not specified, using default negative binomial for state " << i_state;
136
-			NegativeBinomial *d = new NegativeBinomial(O, model->T, initial_r[i_state], initial_p[i_state]);
137
-			model->densityFunctions.push_back(d);
138
-		}
80
+		FILE_LOG(logDEBUG1) << "Using gaussian normal for state " << istate;
81
+		Normal *d = new Normal(O, *T, imean, ivariance); // delete is done inside ~ScaleHMM()
82
+		hmm->densityFunctions.push_back(d);
83
+
139 84
 	}
140 85
 
141 86
 	// Do the Baum-Welch to estimate the parameters
142 87
 	FILE_LOG(logDEBUG1) << "Starting Baum-Welch estimation";
143
-	model->baumWelch(maxiter, maxtime, eps);
88
+	hmm->baumWelch(maxiter, maxtime, eps);
144 89
 	FILE_LOG(logDEBUG1) << "Finished with Baum-Welch estimation";
145 90
 	// Compute the posteriors and save results directly to the R pointer
146
-	double** posteriors = allocDoubleMatrix(model->N, model->T);
147
-	model->get_posteriors(posteriors);
91
+	double** posteriors = allocDoubleMatrix(*N, *T);
92
+	hmm->get_posteriors(posteriors);
148 93
 	FILE_LOG(logDEBUG1) << "Recode posteriors into column representation";
149 94
 	#pragma omp parallel for
150
-	for (int iN=0; iN<model->N; iN++)
95
+	for (int iN=0; iN<*N; iN++)
151 96
 	{
152
-		for (int t=0; t<model->T; t++)
97
+		for (int t=0; t<*T; t++)
153 98
 		{
154
-			post[t + iN * model->T] = posteriors[iN][t];
99
+			post[t + iN * (*T)] = posteriors[iN][t];
155 100
 		}
156 101
 	}
157
-	freeDoubleMatrix(posteriors, model->N);
102
+	freeDoubleMatrix(posteriors, *N);
158 103
 
159 104
 	FILE_LOG(logDEBUG1) << "Return parameters";
160 105
 	// also return the estimated transition matrix and the initial probs
161
-	for (int i=0; i<model->N; i++)
106
+	for (int i=0; i<*N; i++)
162 107
 	{
163
-		proba[i] = model->get_proba(i);
164
-		for (int j=0; j<model->N; j++)
108
+		proba[i] = hmm->get_proba(i);
109
+		for (int j=0; j<*N; j++)
165 110
 		{
166
-          A[i*model->N + j] = model->A[i][j];
111
+			A[i * (*N) + j] = hmm->get_A(i,j);
167 112
 		}
168 113
 	}
169 114
 
170 115
 	// copy the estimated distribution params
171
-	for (int i=0; i<model->N; i++)
116
+	for (int i=0; i<*N; i++)
172 117
 	{
173
-			if (model->densityFunctions[i]->getType() == NB) 
174
-			{
175
-					NegativeBinomial* d = (NegativeBinomial*)(model->densityFunctions[i]);
176
-					r[i] = d->getR();
177
-					p[i] = d->getP();
178
-			}
118
+		means[i] = hmm->densityFunctions[i]->get_mean();
119
+		variances[i] = hmm->densityFunctions[i]->get_variance();
179 120
 	}
180
-	*loglik = model->logP;
181
-	model->calc_weights(softweights);
121
+	*loglik = hmm->get_logP();
122
+	hmm->calc_weights(weights);
182 123
 	
183
-	FILE_LOG(logDEBUG1) << "Deleting the model";
184
-	delete model;
124
+	FILE_LOG(logDEBUG1) << "Deleting the hmm";
125
+	delete hmm;
185 126
 }
186 127
 } // extern C
187 128
 
188
-// ---------------------------------------------------------------
189
-// void R_multivariate_hmm()
190
-// This function takes parameters from R, creates a multivariate HMM object, creates the distributions, runs the Baum-Welch and returns the result to R.
191
-// ---------------------------------------------------------------
192
-extern "C" {
193
-void R_multivariate_hmm(int* O, int* T, int* N, int *Nmod, int* states, double* r, double* p, double* w, double* cor_matrix_inv, double* det, int* maxiter, int* maxtime, double* eps, double* post, double* A, double* proba, double* loglik, double* initial_A, double* initial_proba, bool* use_initial_params, int* num_threads){
194
-
195
-	// Define logging level {"ERROR", "WARNING", "INFO", "ITERATION", "DEBUG", "DEBUG1", "DEBUG2", "DEBUG3", "DEBUG4"}
196
-// 	FILE* pFile = fopen("chromStar.log", "w");
197
-// 	Output2FILE::Stream() = pFile;
198
- 	FILELog::ReportingLevel() = FILELog::FromString("ITERATION");
199
-//  	FILELog::ReportingLevel() = FILELog::FromString("DEBUG");
200
-
201
-	// Parallelization settings
202
-	omp_set_num_threads(*num_threads);
203
-
204
-	// Print some information
205
-	FILE_LOG(logINFO) << "number of states = " << *N;
206
-	FILE_LOG(logINFO) << "number of bins = " << *T;
207
-	if (*maxiter < 0)
208
-	{
209
-		FILE_LOG(logINFO) << "maximum number of iterations = none";
210
-	} else {
211
-		FILE_LOG(logINFO) << "maximum number of iterations = " << *maxiter;
212
-	}
213
-	if (*maxtime < 0)
214
-	{
215
-		FILE_LOG(logINFO) << "maximum running time = none";
216
-	} else {
217
-		FILE_LOG(logINFO) << "maximum running time = " << *maxtime << " sec";
218
-	}
219
-	FILE_LOG(logINFO) << "epsilon = " << *eps;
220
-	FILE_LOG(logINFO) << "number of modifications = " << *Nmod;
221
-
222
-	// Recode the observation vector to matrix representation
223
-	clock_t clocktime = clock(), dtime;
224
-	int** multiO = allocIntMatrix(*Nmod, *T);
225
-	for (int imod=0; imod<*Nmod; imod++)
226
-	{
227
-		for (int t=0; t<*T; t++)
228
-		{
229
-			multiO[imod][t] = O[imod*(*T)+t];
230
-		}
231
-	}
232
-	dtime = clock() - clocktime;
233
-	FILE_LOG(logDEBUG1) << "recoding observation vector to matrix representation: " << dtime << " clicks";
234
-
235
-	// Create the HMM
236
-	FILE_LOG(logDEBUG1) << "Creating the multivariate HMM";
237
-// 	LogHMM* model = new LogHMM(*T, *N, *Nmod);
238
-	ScaleHMM* model = new ScaleHMM(*T, *N, *Nmod);
239
-	// Initialize the transition probabilities and proba
240
-	model->initialize_transition_probs(initial_A, *use_initial_params);
241
-	model->initialize_proba(initial_proba, *use_initial_params);
242
-	
243
-	// Print logproba and A
244
-// 	for (int iN=0; iN<*N; iN++)
245
-// 	{
246
-// 		FILE_LOG(logINFO) << "proba["<<iN<<"] = " <<exp(model->logproba[iN]);
247
-// 		for (int jN=0; jN<*N; jN++)
248
-// 		{
249
-// 			FILE_LOG(logINFO) << "A["<<iN<<"]["<<jN<<"] = " << model->A[iN][jN];
250
-// 		}
251
-// 	}
252
-
253
-	// Prepare the binary_states (univariate) vector: binary_states[N][Nmod], e.g., binary_states[iN][imod] tells me at state states[iN], modification imod is non-enriched (0) or enriched (1)
254
-	FILE_LOG(logDEBUG1) << "Preparing the binary_states vector";
255
-	bool **binary_states = allocBoolMatrix(model->N, model->Nmod);
256
-	for(int iN=0; iN < model->N; iN++) //for each comb state considered
257
-	{
258
-		for(int imod=0; imod < model->Nmod; imod++) //for each modification of this comb state
259
-		{
260
-			binary_states[iN][imod] = states[iN]&(int)pow(2,model->Nmod-imod-1);//if =0->hidden state states[iN] has modification imod non enriched; if !=0->enriched
261
-			if (binary_states[iN][imod] != 0 )
262
-				binary_states[iN][imod] = 1;
263
-		}
264
-	}
265
-
266
-	/* initialize the distributions */
267
-	FILE_LOG(logDEBUG1) << "Initializing the distributions";
268
-	for (int iN=0; iN<model->N; iN++) //for each combinatorial state
269
-	{
270
-		vector <Density*> tempMarginals;            
271
-		for (int imod=0; imod < model->Nmod; imod++) //for each modification
272
-		{
273
-			Density *d;
274
-			if (binary_states[iN][imod]) //construct the marginal density function for modification imod being enriched
275
-			{
276
-				d = new NegativeBinomial(multiO[imod], model->T, r[2*imod+1], p[2*imod+1]); // delete is done inside ~MVCopulaApproximation()
277
-			}
278
-			else //construct the density function for modification imod being non-enriched
279
-			{
280
-				d = new ZiNB(multiO[imod], model->T, r[2*imod], p[2*imod], w[imod]); // delete is done inside ~MVCopulaApproximation()
281
-			}
282
-			tempMarginals.push_back(d);
283
-		}
284
-		//MVCopulaApproximation *tempMVdens = new MVCopulaApproximation(O, tempMarginals, &(cor_matrix_inv[iN*Nmod*Nmod]), det[iN]);
285
-		FILE_LOG(logDEBUG1) << "Calling MVCopulaApproximation for state " << iN;
286
-		MVCopulaApproximation *tempMVdens = new MVCopulaApproximation(multiO, model->T, tempMarginals, &(cor_matrix_inv[iN*model->Nmod*model->Nmod]), det[iN]); // delete is done inside ~LogHMM()
287
-		model->densityFunctions.push_back(tempMVdens);
288
-	}
289
-	
290
-	// Estimate the parameters
291
-	FILE_LOG(logDEBUG1) << "Starting Baum-Welch estimation";
292
-	model->baumWelch(maxiter, maxtime, eps);
293
-	FILE_LOG(logDEBUG1) << "Finished with Baum-Welch estimation";
294
-	
295
-	// Compute the posteriors and save results directly to the R pointer
296
-	double** posteriors = allocDoubleMatrix(model->N, model->T);
297
-	model->get_posteriors(posteriors);
298
-	FILE_LOG(logDEBUG1) << "Recode posteriors into column representation";
299
-	for (int iN=0; iN<model->N; iN++)
300
-	{
301
-		for (int t=0; t<model->T; t++)
302
-		{
303
-			post[t + iN * model->T] = posteriors[iN][t];
304
-		}
305
-	}
306
-	freeDoubleMatrix(posteriors, model->N);
307
-	
308
-	FILE_LOG(logDEBUG1) << "Return parameters";
309
-	// also return the estimated transition matrix and the initial probs
310
-	for (int i=0; i<model->N; i++)
311
-	{
312
-		proba[i] = model->get_proba(i);
313
-		for (int j=0; j<model->N; j++)
314
-		{
315
-				A[i*model->N + j] = model->A[i][j];
316
-		}
317
-	}
318
-	*loglik = model->logP;
319
-
320
-	FILE_LOG(logDEBUG1) << "Deleting the model";
321
-	delete model;
322
-	freeIntMatrix(multiO, *Nmod);
323
-	freeBoolMatrix(binary_states, *N);
324
-}
325
-} // extern C
326
-
327
-// ---------------------------------------------------------------
328
-// void R_multivariate_hmm_productBernoulli()
329
-// This function takes parameters from R, creates a multivariate HMM object, creates the distributions, runs the Baum-Welch and returns the result to R.
330
-// ---------------------------------------------------------------
331
-extern "C" {//observation is now the posterior for being UNMODIFIED
332
-void R_multivariate_hmm_productBernoulli(double* O, int* T, int* N, int *Nmod, int* states, int* maxiter, int* maxtime, double* eps, double* post, double* A, double* proba, double* loglik, double* initial_A, double* initial_proba, bool* use_initial_params, int* num_threads){
333
-
334
-	// Define logging level
335
-// 	FILELog::ReportingLevel() = FILELog::FromString("DEBUG3");
336
-	FILELog::ReportingLevel() = FILELog::FromString("ITERATION");
337
-
338
-	// Parallelization settings
339
-	omp_set_num_threads(*num_threads);
340
-
341
-	// Print some information
342
-	FILE_LOG(logINFO) << "number of states = " << *N;
343
-	FILE_LOG(logINFO) << "number of bins = " << *T;
344
-	if (*maxiter < 0)
345
-	{
346
-		FILE_LOG(logINFO) << "maximum number of iterations = none";
347
-	} else {
348
-		FILE_LOG(logINFO) << "maximum number of iterations = " << *maxiter;
349
-	}
350
-	if (*maxtime < 0)
351
-	{
352
-		FILE_LOG(logINFO) << "maximum running time = none";
353
-	} else {
354
-		FILE_LOG(logINFO) << "maximum running time = " << *maxtime << " sec";
355
-	}
356
-	FILE_LOG(logINFO) << "epsilon = " << *eps;
357
-	FILE_LOG(logINFO) << "number of modifications = " << *Nmod;
358
-
359
-	// Recode the observation vector to matrix representation
360
-	clock_t clocktime = clock(), dtime;
361
-	double** multiO = allocDoubleMatrix(*Nmod, *T);
362
-	for (int imod=0; imod<*Nmod; imod++)
363
-	{
364
-		for (int t=0; t<*T; t++)
365
-		{
366
-			multiO[imod][t] = O[imod*(*T)+t];
367
-		}
368
-	}
369
-	dtime = clock() - clocktime;
370
-	FILE_LOG(logDEBUG1) << "recoding observation and probability vectors to matrix representation: " << dtime << " clicks";
371
-
372
-	// Create the HMM
373
-	FILE_LOG(logDEBUG1) << "Creating the multivariate HMM";
374
-	LogHMM* model = new LogHMM(*T, *N, *Nmod);
375
-
376
-	// Initialize the transition probabilities and proba
377
-	model->initialize_transition_probs(initial_A, *use_initial_params);
378
-	model->initialize_proba(initial_proba, *use_initial_params);
379
-	
380
-	// Print logproba and A
381
-// 	for (int iN=0; iN<*N; iN++)
382
-// 	{
383
-// 		FILE_LOG(logINFO) << "proba["<<iN<<"] = " <<exp(model->logproba[iN]);
384
-// 		for (int jN=0; jN<*N; jN++)
385
-// 		{
386
-// 			FILE_LOG(logINFO) << "A["<<iN<<"]["<<jN<<"] = " << model->A[iN][jN];
387
-// 		}
388
-// 	}
389
-
390
-	// Prepare the binary_states (univariate) vector: binary_states[N][Nmod], e.g., binary_states[iN][imod] tells me at state states[iN], modification imod is non-enriched (0) or enriched (1)
391
-	FILE_LOG(logDEBUG1) << "Preparing the binary_states vector";
392
-	bool **binary_states = allocBoolMatrix(model->N, model->Nmod);
393
-	for(int iN=0; iN < model->N; iN++) //for each comb state considered
394
-	{
395
-		for(int imod=0; imod < model->Nmod; imod++) //for each modification of this comb state
396
-		{
397
-			binary_states[iN][imod] = states[iN]&(int)pow(2,model->Nmod-imod-1);//if =0->hidden state states[iN] has modification imod non enriched; if !=0->enriched
398
-			if (binary_states[iN][imod] != 0 )
399
-				binary_states[iN][imod] = 1;
400
-		}
401
-	}
402
-
403
-	/* initialize the distributions */
404
-	FILE_LOG(logDEBUG1) << "Initializing the distributions";
405
-	for (int iN=0; iN<model->N; iN++) //for each combinatorial state
406
-	{
407
-		FILE_LOG(logDEBUG1) << "Calling BernoulliProduct";
408
-		BernoulliProduct *tempBP = new BernoulliProduct(multiO, binary_states[iN], *T, *Nmod); // delete is done inside ~LogHMM()
409
-		model->densityFunctions.push_back(tempBP);
410
-	}
411
-
412
-	// Estimate the parameters
413
-	FILE_LOG(logDEBUG1) << "Starting Baum-Welch estimation";
414
-	model->baumWelch(maxiter, maxtime, eps);
415
-	FILE_LOG(logDEBUG1) << "Finished with Baum-Welch estimation";
416
-	
417
-    // Compute the posteriors and save results directly to the R pointer
418
-    double** posteriors = allocDoubleMatrix(model->N, model->T);
419
-    model->get_posteriors(posteriors);
420
-	FILE_LOG(logDEBUG1) << "Recode posteriors into column representation";
421
-	for (int iN=0; iN<model->N; iN++)
422
-	{
423
-		for (int t=0; t<model->T; t++)
424
-		{
425
-			post[t + iN * model->T] = posteriors[iN][t];
426
-		}
427
-	}
428
-    freeDoubleMatrix(posteriors, model->N);
429
-	
430
-	FILE_LOG(logDEBUG1) << "Return parameters";
431
-	// also return the estimated transition matrix and the initial probs
432
-	for (int i=0; i<model->N; i++)
433
-	{
434
-		proba[i] = model->get_proba(i);
435
-		for (int j=0; j<model->N; j++)
436
-		{
437
-				A[i*model->N + j] = model->A[i][j];
438
-		}
439
-	}
440
-	*loglik = model->logP;
441
-
442
-	FILE_LOG(logDEBUG1) << "Deleting the model";
443
-	delete model;
444
-	freeDoubleMatrix(multiO, *Nmod);
445
-	freeBoolMatrix(binary_states, *N);
446
-}
447
-} // extern C
... ...
@@ -1,1128 +1,86 @@
1 1
 #include "densities.h"
2
-#include "utility.h"
3 2
 
4
-// ------------------------------------------------------------
5
-// Zero inflated negative binomial
6
-// ------------------------------------------------------------
3
+// ============================================================
4
+// Normal (Gaussian) density
5
+// ============================================================
7 6
 
8
-ZiNB::ZiNB()
9
-{
10
-	this->lxfactorials = NULL;
11
-}
12
-
13
-ZiNB::ZiNB(int* observations, int T, double r, double p, double w)
7
+// Constructor and Destructor ---------------------------------
8
+Normal::Normal(int* observations, int T, double mean, double variance)
14 9
 {
15 10
 	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
16
-	this->O = observations;
11
+	this->obs = observations;
17 12
 	this->T = T;
18
-	this->p = p;
19
-	this->r = r;
20
-	this->w = w;
21
-	this->lxfactorials = NULL;
22
-	if (this->O != NULL)
23
-	{
24
-		this->max_O = intMax(observations, T);
25
-		this->lxfactorials = (double*) calloc(max_O+1, sizeof(double));
26
-		this->lxfactorials[0] = 0.0;	// Not necessary, already 0 because of calloc
27
-		this->lxfactorials[1] = 0.0;
28
-		for (int j=2; j<=max_O; j++)
29
-		{
30
-			this->lxfactorials[j] = this->lxfactorials[j-1] + log(j);
31
-		}
32
-	}
13
+	this->mean = mean;
14
+	this->var = variance;
15
+	this->sd = sqrt(variance);
33 16
 }
34 17
 
35
-ZiNB::~ZiNB()
18
+Normal::~Normal()
36 19
 {
37 20
 	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
38
-	if (this->O != NULL)
39
-	{
40
-		free(this->lxfactorials);
41
-	}
42 21
 }
43 22
 
44
-void ZiNB::calc_logdensities(double* logdens)
45
-{
46
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
47
-	double logp = log(this->p);
48
-	double log1minusp = log(1-this->p);
49
-	double lGammaR,lGammaRplusX,lxfactorial;
50
-	lGammaR=lgamma(this->r);
51
-	// Select strategy for computing gammas
52
-	if (this->max_O <= this->T)
53
-	{
54
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
55
-		double lGammaRplusX[this->max_O+1];
56
-		for (int j=0; j<=this->max_O; j++)
57
-		{
58
-			lGammaRplusX[j] = lgamma(this->r + j);
59
-		}
60
-		for (int t=0; t<this->T; t++)
61
-		{
62
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
63
-			if (O[t] == 0)
64
-			{
65
-				logdens[t] = log( this->w + (1-this->w) * exp( lGammaRplusX[(int) this->O[t]] - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp ) );
66
-			}
67
-			else
68
-			{
69
-				logdens[t] = log(1-this->w) + lGammaRplusX[(int) this->O[t]] - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp;
70
-			}
71
-			if (isnan(logdens[t]))
72
-			{
73
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
74
-				FILE_LOG(logWARNING) << "logdens["<<t<<"] = "<< logdens[t];
75
-				exit(1);
76
-			}
77
-		}
78
-	}
79
-	else
80
-	{
81
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
82
-		for (int t=0; t<this->T; t++)
83
-		{
84
-			lGammaRplusX = lgamma(this->r + this->O[t]);
85
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
86
-			if (O[t] == 0)
87
-			{
88
-				logdens[t] = log( this->w + (1-this->w) * exp( lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp ) );
89
-			}
90
-			else
91
-			{
92
-				logdens[t] = log(1-this->w) + lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp;
93
-			}
94
-			if (isnan(logdens[t]))
95
-			{
96
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
97
-				FILE_LOG(logWARNING) << "logdens["<<t<<"] = "<< logdens[t];
98
-				exit(1);
99
-			}
100
-		}
101
-	}
102
-}
103
-
104
-void ZiNB::calc_densities(double* dens)
105
-{
106
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
107
-	double logp = log(this->p);
108
-	double log1minusp = log(1-this->p);
109
-	double lGammaR,lGammaRplusX,lxfactorial;
110
-	lGammaR=lgamma(this->r);
111
-	// Select strategy for computing gammas
112
-	if (this->max_O <= this->T)
113
-	{
114
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
115
-		double lGammaRplusX[this->max_O+1];
116
-		for (int j=0; j<=this->max_O; j++)
117
-		{
118
-			lGammaRplusX[j] = lgamma(this->r + j);
119
-		}
120
-		for (int t=0; t<this->T; t++)
121
-		{
122
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
123
-			if (O[t] == 0)
124
-			{
125
-				dens[t] = this->w + (1-this->w) * exp( lGammaRplusX[(int) this->O[t]] - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp );
126
-			}
127
-			else
128
-			{
129
-				dens[t] = (1-this->w) * exp( lGammaRplusX[(int) this->O[t]] - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp );
130
-			}
131
-			if (isnan(dens[t]))
132
-			{
133
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
134
-				FILE_LOG(logWARNING) << "dens["<<t<<"] = "<< dens[t];
135
-				exit(1);
136
-			}
137
-		}
138
-	}
139
-	else
140
-	{
141
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
142
-		for (int t=0; t<this->T; t++)
143
-		{
144
-			lGammaRplusX = lgamma(this->r + this->O[t]);
145
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
146
-			if (O[t] == 0)
147
-			{
148
-				dens[t] = this->w + (1-this->w) * exp( lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp );
149
-			}
150
-			else
151
-			{
152
-				dens[t] = (1-this->w) * exp( lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp );
153
-			}
154
-			if (isnan(dens[t]))
155
-			{
156
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
157
-				FILE_LOG(logWARNING) << "dens["<<t<<"] = "<< dens[t];
158
-				exit(1);
159
-			}
160
-		}
161
-	}
162
-}
163
-
164
-void ZiNB::calc_CDFs(double* CDF)
165
-{
166
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
167
-	double log1minusp = log(1-this->p);
168
-	double lGammaR = lgamma(this->r);
169
-	double lppowerr = this->r * log(this->p);
170
-	// No selection strategy here, because we must precompute CDF to deal with 1s by shifting them
171
-// 	// Select strategy for computing gammas
172
-// 	if (this->max_O <= this->T)
173
-//	{
174
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
175
-		double lGamma1plusRplusX[this->max_O+1], lGamma2plusX[this->max_O+1], lHyper[this->max_O+1], lppowert[this->max_O+1];
176
-		double precomputed_CDF[this->max_O+1];
177
-		for (int j=0; j<=this->max_O; j++)
178
-		{
179
-			lGamma1plusRplusX[j] = lgamma(1 + this->r + j);
180
-			lGamma2plusX[j] = lgamma(2 + j);
181
-			lHyper[j] = log(gsl_sf_hyperg_2F1(1, 1 + this->r + j, 2 + j, 1-this->p));
182
-			lppowert[j] = (1+j) * log1minusp;
183
-			precomputed_CDF[j] = 1 - exp( log(1-this->w) + lppowerr + lppowert[j] + lGamma1plusRplusX[j] + lHyper[j] - lGammaR - lGamma2plusX[j] );
184
-			if (precomputed_CDF[j] == 1)
185
-			{
186
-				FILE_LOG(logDEBUG4) << "CDF = 1 for O[t] = "<<j<< ", shifting to value of O[t] = "<<j-1;
187
-				precomputed_CDF[j] = precomputed_CDF[j-1]; 
188
-			}
189
-		}
190
-		for (int t=0; t<this->T; t++)
191
-		{
192
-			CDF[t] = precomputed_CDF[(int)O[t]];
193
-			if (isnan(CDF[t]))
194
-			{
195
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
196
-				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t];
197
-				exit(1);
198
-			}
199
-		}
200
-// 	}
201
-// 	else
202
-// 	{
203
-// 		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
204
-// 		double lGamma1plusRplusX, lGamma2plusX, lHyper, lppowert;
205
-// 		for (int t=0; t<this->T; t++)
206
-//		{
207
-// 			lGamma1plusRplusX = lgamma(1 + this->r + this->O[t]);
208
-// 			lGamma2plusX = lgamma(2 + this->O[t]);
209
-// 			lHyper = log(gsl_sf_hyperg_2F1(1, 1 + this->r + this->O[t], 2 + this->O[t], 1-this->p));
210
-// 			lppowert = (1+this->O[t]) * log1minusp;
211
-// 			CDF[t] = 1 - exp( log(1-this->w) + lppowerr + lppowert + lGamma1plusRplusX + lHyper - lGammaR - lGamma2plusX ); //TODO: Check formula for log
212
-// 			if(CDF[t] == 0)
213
-// 			{
214
-// 				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t]; //TODO: Check if this works
215
-// // 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
216
-// 			}
217
-// 			if (isnan(CDF[t]))
218
-// 			{
219
-// 				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
220
-// 				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t];
221
-// 				exit(1);
222
-// 			}
223
-// 		}
224
-// 	}
225
-}
226
-
227
-void ZiNB::calc_logCDFs(double* logCDF)
228
-{
229
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
230
-	double log1minusp = log(1-this->p);
231
-	double lGamma1plusRplusX, lHyper, lGammaR, lGamma2plusX, lppowert, lppowerr;
232
-	lGammaR = lgamma(this->r);
233
-	lppowerr = this->r * log(this->p);
234
-	// Select strategy for computing gammas
235
-	if (this->max_O <= this->T)
236
-	{
237
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
238
-		double lGamma1plusRplusX[this->max_O+1], lGamma2plusX[this->max_O+1], lHyper[this->max_O+1], lppowert[this->max_O+1];
239
-		for (int j=0; j<=this->max_O; j++)
240
-		{
241
-			lGamma1plusRplusX[j] = lgamma(1 + this->r + j);
242
-			lGamma2plusX[j] = lgamma(2 + j);
243
-			lHyper[j] = log(gsl_sf_hyperg_2F1(1, 1 + this->r + j, 2 + j, 1-this->p));
244
-			lppowert[j] = (1+j) * log1minusp;
245
-		}
246
-		for (int t=0; t<this->T; t++)
247
-		{
248
-			logCDF[t] = log(1 - exp( log(1-this->w) + lppowerr + lppowert[(int)O[t]] + lGamma1plusRplusX[(int)O[t]] + lHyper[(int)O[t]] - lGammaR - lGamma2plusX[(int)O[t]] ));
249
-			if(logCDF[t] == 0)
250
-			{
251
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = 0";
252
-// 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
253
-			}
254
-			if (isnan(logCDF[t]))
255
-			{
256
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
257
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = "<< logCDF[t];
258
-				exit(1);
259
-			}
260
-		}
261
-	}
262
-	else
263
-	{
264
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
265
-		for (int t=0; t<this->T; t++)
266
-		{
267
-			lGamma1plusRplusX = lgamma(1 + this->r + this->O[t]);
268
-			lGamma2plusX = lgamma(2 + this->O[t]);
269
-			lHyper = log(gsl_sf_hyperg_2F1(1, 1 + this->r + this->O[t], 2 + this->O[t], 1-this->p));
270
-			lppowert = (1+this->O[t]) * log1minusp;
271
-			logCDF[t] = log(1 - exp( log(1-this->w) + lppowerr + lppowert + lGamma1plusRplusX + lHyper - lGammaR - lGamma2plusX )); //TODO: Check formula for log
272
-			if(logCDF[t] == 0)
273
-			{
274
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = 0"; //TODO: Check if this works
275
-// 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
276
-			}
277
-			if (isnan(logCDF[t]))
278
-			{
279
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
280
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = "<< logCDF[t];
281
-				exit(1);
282
-			}
283
-		}
284
-	}
285
-}
286
-
287
-double ZiNB::getMean()
288
-{
289
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
290
-	return (1-this->w)*this->r*(1-this->p)/this->p;
291
-}
292
-
293
-double ZiNB::getVariance()
294
-{
295
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
296
-	return (1-this->w)*this->r*(1-this->p)/this->p/this->p; //TODO: Is this correct?
297
-}
298
-
299
-DensityName ZiNB::getType()
300
-{
301
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
302
-	return(ZINB);
303
-}
304
-
305
-void ZiNB::setR (double newR)
306
-{
307
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
308
-  this->r = newR;
309
-}
310
-
311
-double ZiNB::getR()
312
-{
313
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
314
-  return(this->r);
315
-}
316
-
317
-void ZiNB::setP (double newP)
318
-{
319
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
320
-  this->p = newP;
321
-}
322
-
323
-double ZiNB::getP()
324
-{
325
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
326
-  return(this->p);
327
-}
328
-
329
-void ZiNB::setW (double newW)
330
-{
331
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
332
-    this->w = newW;
333
-}
334
-
335
-double ZiNB::getW()
336
-{
337
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
338
-	return(this->w);
339
-}
340
-
341
-void ZiNB::copy(Density* other)
342
-{
343
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
344
-	ZiNB* o = (ZiNB*)other;
345
-	this->p = o->p;
346
-	this->r = o->r;
347
-	this->O = o->O;
348
-	this->w = o->w;
349
-}
350
-
351
-double ZiNB::getLogDensityAt10Variance()
352
-{
353
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
354
-	double logp = log(this->p);
355
-	double log1minusp = log(1-this->p);
356
-	double lGammaR,lGammaRplusX,lxfactorial;
357
-	double logdens;
358
-	// Calculate variance
359
-	double mean = 0, variance = 0;
360
-	for(int t=0; t<this->T; t++)
361
-	{
362
-		mean += O[t];
363
-	}
364
-	mean = mean / this->T;
365
-	for(int t=0; t<this->T; t++)
366
-	{
367
-		variance += pow(O[t] - mean, 2);
368
-	}
369
-	variance = variance / this->T;
370
-	// Calculate logdensity
371
-	int x = 10*((int)variance+1);
372
-	lGammaR=lgamma(this->r);
373
-	lGammaRplusX = lgamma(this->r + x);
374
-	lxfactorial = this->lxfactorials[x];
375
-	if (x == 0)
376
-	{
377
-		logdens = log( this->w + (1-this->w) * exp( lGammaRplusX - lGammaR - lxfactorial + this->r * logp + x * log1minusp ) );
378
-	}
379
-	else
380
-	{
381
-		logdens = log(1-this->w) + lGammaRplusX - lGammaR - lxfactorial + this->r * logp + x * log1minusp;
382
-	}
383
-	if (isnan(logdens))
384
-	{
385
-		FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
386
-		FILE_LOG(logWARNING) << "logdens = "<< logdens;
387
-		exit(1);
388
-	}
389
-	
390
-	return(logdens);
391
-}
392
-
393
-
394
-// ------------------------------------------------------------
395
-// Negative binomial
396
-// ------------------------------------------------------------
397
-
398
-NegativeBinomial::NegativeBinomial()
399
-{
400
-	this->lxfactorials = NULL;
401
-}
402
-
403
-NegativeBinomial::NegativeBinomial(int* observations, int T, double r, double p)
404
-{
405
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
406
-	this->O = observations;
407
-	this->T = T;
408
-	this->r = r;
409
-	this->p = p;
410
-	this->lxfactorials = NULL;
411
-	// Precompute the lxfactorials that are used in computing the densities
412
-	if (this->O != NULL)
413
-	{
414
-		this->max_O = intMax(observations, T);
415
-		this->lxfactorials = (double*) calloc(max_O+1, sizeof(double));
416
-		this->lxfactorials[0] = 0.0;	// Not necessary, already 0 because of calloc
417
-		this->lxfactorials[1] = 0.0;
418
-		for (int j=2; j<=max_O; j++)
419
-		{
420
-			this->lxfactorials[j] = this->lxfactorials[j-1] + log(j);
421
-		}
422
-	}
423
-}
424
-
425
-NegativeBinomial::~NegativeBinomial()
426
-{
427
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
428
-	if (this->lxfactorials != NULL)
429
-	{
430
-		free(this->lxfactorials);
431
-	}
432
-}
433
-
434
-void NegativeBinomial::calc_logdensities(double* logdens)
435
-{
436
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
437
-	double logp = log(this->p);
438
-	double log1minusp = log(1-this->p);
439
-	double lGammaR,lGammaRplusX,lxfactorial;
440
-	lGammaR=lgamma(this->r);
441
-	// Select strategy for computing gammas
442
-	if (this->max_O <= this->T)
443
-	{
444
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
445
-		double logdens_per_read [this->max_O+1];
446
-		for (int j=0; j<=this->max_O; j++)
447
-		{
448
-			logdens_per_read[j] = lgamma(this->r + j) - lGammaR - lxfactorials[j] + this->r * logp + j * log1minusp;
449
-		}
450
-		for (int t=0; t<this->T; t++)
451
-		{
452
-			logdens[t] = logdens_per_read[(int) this->O[t]];
453
-			FILE_LOG(logDEBUG4) << "logdens["<<t<<"] = " << logdens[t];
454
-			if (isnan(logdens[t]))
455
-			{
456
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
457
-				FILE_LOG(logWARNING) << "logdens["<<t<<"] = "<< logdens[t];
458
-				exit(1);
459
-			}
460
-		}
461
-	}
462
-	else
463
-	{
464
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
465
-		for (int t=0; t<this->T; t++)
466
-		{
467
-			lGammaRplusX = lgamma(this->r + this->O[t]);
468
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
469
-			logdens[t] = lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp;
470
-			FILE_LOG(logDEBUG4) << "logdens["<<t<<"] = " << logdens[t];
471
-			if (isnan(logdens[t]))
472
-			{
473
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
474
-				FILE_LOG(logWARNING) << "logdens["<<t<<"] = "<< logdens[t];
475
-				exit(1);
476
-			}
477
-		}
478
-	}
479
-} 
480
-
481
-void NegativeBinomial::calc_densities(double* dens)
482
-{
483
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
484
-	double logp = log(this->p);
485
-	double log1minusp = log(1-this->p);
486
-	double lGammaR,lGammaRplusX,lxfactorial;
487
-	lGammaR=lgamma(this->r);
488
-	// Select strategy for computing gammas
489
-	if (this->max_O <= this->T)
490
-	{
491
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
492
-		double dens_per_read [this->max_O+1];
493
-		for (int j=0; j<=this->max_O; j++)
494
-		{
495
-			dens_per_read[j] = exp( lgamma(this->r + j) - lGammaR - lxfactorials[j] + this->r * logp + j * log1minusp );
496
-		}
497
-		for (int t=0; t<this->T; t++)
498
-		{
499
-			dens[t] = dens_per_read[(int) this->O[t]];
500
-			FILE_LOG(logDEBUG4) << "dens["<<t<<"] = " << dens[t];
501
-			if (isnan(dens[t]))
502
-			{
503
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
504
-				FILE_LOG(logWARNING) << "dens["<<t<<"] = "<< dens[t];
505
-				exit(1);
506
-			}
507
-		}
508
-	}
509
-	else
510
-	{
511
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
512
-		for (int t=0; t<this->T; t++)
513
-		{
514
-					lGammaRplusX = lgamma(this->r + this->O[t]);
515
-			lxfactorial = this->lxfactorials[(int) this->O[t]];
516
-			dens[t] = exp( lGammaRplusX - lGammaR - lxfactorial + this->r * logp + this->O[t] * log1minusp );
517
-			FILE_LOG(logDEBUG4) << "dens["<<t<<"] = " << dens[t];
518
-			if (isnan(dens[t]))
519
-			{
520
-							FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
521
-				FILE_LOG(logWARNING) << "dens["<<t<<"] = "<< dens[t];
522
-				exit(1);
523
-			}
524
-		}
525
-	}
526
-} 
527
-
528
-void NegativeBinomial::calc_CDFs(double* CDF)
529
-{
530
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
531
-	double log1minusp = log(1-this->p);
532
-	double lGammaR = lgamma(this->r);
533
-	double lppowerr = this->r * log(this->p);
534
-	// No selection strategy here, because we must precompute CDF to deal with 1s by shifting them
535
-// 	// Select strategy for computing gammas
536
-// 	if (this->max_O <= this->T)
537
-// 	{
538
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
539
-		double lGamma1plusRplusX[this->max_O+1], lGamma2plusX[this->max_O+1], lHyper[this->max_O+1], lppowert[this->max_O+1];
540
-		double precomputed_CDF[this->max_O+1];
541
-		for (int j=0; j<=this->max_O; j++)
542
-		{
543
-			lGamma1plusRplusX[j] = lgamma(1 + this->r + j);
544
-			lGamma2plusX[j] = lgamma(2 + j);
545
-			lHyper[j] = log(gsl_sf_hyperg_2F1(1, 1 + this->r + j, 2 + j, 1-this->p));
546
-			lppowert[j] = (1+j) * log1minusp;
547
-			precomputed_CDF[j] = 1 - exp( lppowerr + lppowert[j] + lGamma1plusRplusX[j] + lHyper[j] - lGammaR - lGamma2plusX[j] );
548
-			if (precomputed_CDF[j] == 1)
549
-			{
550
-				FILE_LOG(logDEBUG4) << "CDF = 1 for O[t] = "<<j<< ", shifting to value of O[t] = "<<j-1;
551
-				precomputed_CDF[j] = precomputed_CDF[j-1]; 
552
-			}
553
-		}
554
-		for (int t=0; t<this->T; t++)
555
-		{
556
-			CDF[t] = precomputed_CDF[(int)O[t]];
557
-			if (isnan(CDF[t]))
558
-			{
559
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
560
-				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t];
561
-				exit(1);
562
-			}
563
-		}
564
-// 	}
565
-// 	else
566
-// 	{
567
-// 		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
568
-// 		double lGamma1plusRplusX, lGamma2plusX, lHyper, lppowert;
569
-// 		for (int t=0; t<this->T; t++)
570
-// 		{
571
-// 			lGamma1plusRplusX = lgamma(1 + this->r + this->O[t]);
572
-// 			lGamma2plusX = lgamma(2 + this->O[t]);
573
-// 			lHyper = log(gsl_sf_hyperg_2F1(1, 1 + this->r + this->O[t], 2 + this->O[t], 1-this->p));
574
-// 			lppowert = (1+this->O[t]) * log1minusp;
575
-// 			CDF[t] = 1 - exp( lppowerr + lppowert + lGamma1plusRplusX + lHyper - lGammaR - lGamma2plusX ); //TODO: Check formula for log
576
-// 			if(CDF[t] == 1)
577
-// 			{
578
-// 				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t]; //TODO: Check if this works
579
-// // 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
580
-// 			}
581
-// 			if (isnan(CDF[t]))
582
-// 			{
583
-// 				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
584
-// 				FILE_LOG(logWARNING) << "CDF["<<t<<"] = "<< CDF[t];
585
-// 				exit(1);
586
-// 			}
587
-// 		}
588
-// 	}
589
-}
590
-
591
-void NegativeBinomial::calc_logCDFs(double* logCDF)
592
-{
593
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
594
-	double log1minusp = log(1-this->p);
595
-	double lGamma1plusRplusX, lHyper, lGammaR, lGamma2plusX, lppowert, lppowerr;
596
-	lGammaR = lgamma(this->r);
597
-	lppowerr = this->r * log(this->p);
598
-	// Select strategy for computing gammas
599
-	if (this->max_O <= this->T)
600
-	{
601
-		FILE_LOG(logDEBUG2) << "Precomputing gammas in " << __func__ << " for every O[t], because max(O)<=T";
602
-		double lGamma1plusRplusX[this->max_O+1], lGamma2plusX[this->max_O+1], lHyper[this->max_O+1], lppowert[this->max_O+1];
603
-		for (int j=0; j<=this->max_O; j++)
604
-		{
605
-			lGamma1plusRplusX[j] = lgamma(1 + this->r + j);
606
-			lGamma2plusX[j] = lgamma(2 + j);
607
-			lHyper[j] = log(gsl_sf_hyperg_2F1(1, 1 + this->r + j, 2 + j, 1-this->p));
608
-			lppowert[j] = (1+j) * log1minusp;
609
-		}
610
-		for (int t=0; t<this->T; t++)
611
-		{
612
-			logCDF[t] = log(1 - exp( lppowerr + lppowert[(int)O[t]] + lGamma1plusRplusX[(int)O[t]] + lHyper[(int)O[t]] - lGammaR - lGamma2plusX[(int)O[t]] ));
613
-			if(logCDF[t] == 0)
614
-			{
615
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = 0";
616
-// 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
617
-			}
618
-			if (isnan(logCDF[t]))
619
-			{
620
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
621
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = "<< logCDF[t];
622
-				exit(1);
623
-			}
624
-		}
625
-	}
626
-	else
627
-	{
628
-		FILE_LOG(logDEBUG2) << "Computing gammas in " << __func__ << " for every t, because max(O)>T";
629
-		for (int t=0; t<this->T; t++)
630
-		{
631
-			lGamma1plusRplusX = lgamma(1 + this->r + this->O[t]);
632
-			lGamma2plusX = lgamma(2 + this->O[t]);
633
-			lHyper = log(gsl_sf_hyperg_2F1(1, 1 + this->r + this->O[t], 2 + this->O[t], 1-this->p));
634
-			lppowert = (1+this->O[t]) * log1minusp;
635
-			logCDF[t] = log(1 - exp( lppowerr + lppowert + lGamma1plusRplusX + lHyper - lGammaR - lGamma2plusX )); //TODO: Check formula for log
636
-			if(logCDF[t] == 0)
637
-			{
638
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = 1"; //TODO: Check if this works
639
-// 				cout<<"CAUTION!!!! current ="<<current<<endl; current = this->cdf->at(i-1);
640
-			}
641
-			if (isnan(logCDF[t]))
642
-			{
643
-				FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
644
-				FILE_LOG(logWARNING) << "logCDF["<<t<<"] = "<< logCDF[t];
645
-				exit(1);
646
-			}
647
-		}
648
-	}
649
-}
650
-
651
-void NegativeBinomial::update(double* weight)
652
-{
653
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
654
-	double eps = 1e-4, kmax;
655
-	double numerator, denominator, rhere, dr, Fr, dFrdr, DigammaR, DigammaRplusDR;
656
-	// Update p
657
-	numerator=denominator=0.0;
658
-	clock_t time, dtime;
659
-	time = clock();
660
-	for (int t=0; t<this->T; t++)
661
-	{
662
-		numerator+=weight[t]*this->r;
663
-		denominator+=weight[t]*(this->r+this->O[t]);
664
-	}
665
-	this->p = numerator/denominator; // Update of r is now done with updated p
666
-	double logp = log(this->p);
667
-	dtime = clock() - time;
668
-	FILE_LOG(logDEBUG1) << "updateP(): "<<dtime<< " clicks";
669
-	// Update of r with Newton Method
670
-	rhere = this->r;
671
-	dr = 0.00001;
672
-	kmax = 20;
673
-	time = clock();
674
-	// Select strategy for computing digammas
675
-	if (this->max_O <= this->T)
676
-	{
677
-		FILE_LOG(logDEBUG2) << "Precomputing digammas in " << __func__ << " for every O[t], because max(O)<=T";
678
-		double DigammaRplusX[this->max_O+1], DigammaRplusDRplusX[this->max_O+1];
679
-		for (int k=1; k<kmax; k++)
680
-		{
681
-			Fr=dFrdr=0.0;
682
-			DigammaR = digamma(rhere); // boost::math::digamma<>(rhere);
683
-			DigammaRplusDR = digamma(rhere + dr); // boost::math::digamma<>(rhere+dr);
684
-			// Precompute the digammas by iterating over all possible values of the observation vector
685
-			for (int j=0; j<=this->max_O; j++)
686
-			{
687
-				DigammaRplusX[j] = digamma(rhere+j);
688
-				DigammaRplusDRplusX[j] = digamma(rhere+dr+j);
689
-			}
690
-			for(int t=0; t<this->T; t++)
691
-			{
692
-				if(this->O[t]==0)
693
-				{
694
-					Fr+=weight[t]*logp;
695
-					//dFrdr+=0;
696
-				}
697
-				if(this->O[t]!=0)
698
-				{
699
-					Fr+=weight[t]*(logp-DigammaR+DigammaRplusX[(int)O[t]]);
700
-					dFrdr+=weight[t]/dr*(DigammaR-DigammaRplusDR+DigammaRplusDRplusX[(int)O[t]]-DigammaRplusX[(int)O[t]]);
701
-				}
702
-			}
703
-			if(fabs(Fr)<eps)
704
-{
705
-				break;
706
-			}
707
-			if(Fr/dFrdr<rhere) rhere=rhere-Fr/dFrdr;
708
-			if(Fr/dFrdr>rhere) rhere=rhere/2.0;
709
-		}
710
-	}
711
-	else
712
-	{
713
-		FILE_LOG(logDEBUG2) << "Computing digammas in " << __func__ << " for every t, because max(O)>T";
714
-		double DigammaRplusX, DigammaRplusDRplusX;
715
-		for (int k=1; k<kmax; k++)
716
-		{
717
-			Fr = dFrdr = 0.0;
718
-			DigammaR = digamma(rhere); // boost::math::digamma<>(rhere);
719
-			DigammaRplusDR = digamma(rhere + dr); // boost::math::digamma<>(rhere+dr);
720
-			for(int t=0; t<this->T; t++)
721
-			{
722
-				DigammaRplusX = digamma(rhere+this->O[t]); //boost::math::digamma<>(rhere+this->O[ti]);
723
-				DigammaRplusDRplusX = digamma(rhere+dr+this->O[t]); // boost::math::digamma<>(rhere+dr+this->O[ti]);
724
-				if(this->O[t]==0)
725
-				{
726
-					Fr+=weight[t]*logp;
727
-					//dFrdr+=0;
728
-				}
729
-				if(this->O[t]!=0)
730
-				{
731
-					Fr+=weight[t]*(logp-DigammaR+DigammaRplusX);
732
-					dFrdr+=weight[t]/dr*(DigammaR-DigammaRplusDR+DigammaRplusDRplusX-DigammaRplusX);
733
-				}
734
-			}
735
-			if(fabs(Fr)<eps)
736
-			{
737
-				break;
738
-			}
739
-			if(Fr/dFrdr<rhere) rhere=rhere-Fr/dFrdr;
740
-			if(Fr/dFrdr>rhere) rhere=rhere/2.0;
741
-		}
742
-	}
743
-	this->r = rhere;
744
-	FILE_LOG(logDEBUG1) << "r = "<<this->r << ", p = "<<this->p;
745
-
746
-	dtime = clock() - time;
747
-	FILE_LOG(logDEBUG1) << "updateR(): "<<dtime<< " clicks";
748
-
749
-}
750
-
751
-double NegativeBinomial::getMean()
752
-{
753
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
754
-	return this->r*(1-this->p)/this->p;
755
-}
756
-
757
-double NegativeBinomial::getVariance()
758
-{
759
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
760
-	return this->r*(1-this->p)/this->p/this->p;
761
-}
762
-
763
-DensityName NegativeBinomial::getType()
764
-{
765
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
766
-	return(NB);
767
-}
768
-
769
-void NegativeBinomial::setR (double newR)
770
-{
771
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
772
-	this->r = newR;
773
-}
774
-
775
-double NegativeBinomial::getR()
776
-{
777
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
778
-	return(this->r);
779
-}
780
-
781
-void NegativeBinomial::setP (double newP)
782
-{
783
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
784
-	this->p = newP;
785
-}
786
-
787
-double NegativeBinomial::getP()
788
-{
789
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
790
-	return(this->p);
791
-}
792
-
793
-void NegativeBinomial::copy(Density* other)
794
-{
795
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
796
-	NegativeBinomial* o = (NegativeBinomial*)other;
797
-	this->p = o->p;
798
-	this->r = o->r;
799
-	this->O = o->O;
800
-}
801
-
802
-double NegativeBinomial::getLogDensityAt10Variance()
803
-{
804
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
805
-	double logp = log(this->p);
806
-	double log1minusp = log(1-this->p);
807
-	double lGammaR,lGammaRplusX,lxfactorial;
808
-	double logdens;
809
-	// Calculate variance
810
-	double mean = 0, variance = 0;
811
-	for(int t=0; t<this->T; t++)
812
-	{
813
-		mean += O[t];
814
-	}
815
-	mean = mean / this->T;
816
-	for(int t=0; t<this->T; t++)
817
-	{
818
-		variance += pow(O[t] - mean, 2);
819
-	}
820
-	variance = variance / this->T;
821
-	// Calculate logdensity
822
-	int x = 10*((int)variance+1);
823
-	lGammaR=lgamma(this->r);
824
-	lGammaRplusX = lgamma(this->r + x);
825
-	lxfactorial = this->lxfactorials[x];
826
-	logdens = lGammaRplusX - lGammaR - lxfactorial + this->r * logp + x * log1minusp;
827
-	if (isnan(logdens))
828
-	{
829
-		FILE_LOG(logWARNING) << __PRETTY_FUNCTION__;
830
-		FILE_LOG(logWARNING) << "logdens = "<< logdens;
831
-		exit(1);
832
-	}
833
-	
834
-	return(logdens);
835
-}
836
-
837
-
838
-// ------------------------------------------------------------
839
-// Only zeros
840
-// ------------------------------------------------------------
841
-
842
-OnlyZeros::OnlyZeros() {}
843
-
844
-OnlyZeros::OnlyZeros(int* observations, int T)
845
-{
846
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
847
-	this->O = observations;
848
-	this->T = T;
849
-}
850
-
851
-OnlyZeros::~OnlyZeros()
852
-{
853
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
854
-}
855
-
856
-void OnlyZeros::calc_logdensities(double* logdens)
23
+// Methods ----------------------------------------------------
24
+void Normal::calc_densities(double* density)
857 25
 {
858 26
 	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
859 27
 	for (int t=0; t<this->T; t++)
860 28
 	{
861
-		if(O[t]==0)
862
-		{
863
-			logdens[t] = 0.0;
864
-		};
865
-		if(O[t]>0)
866
-		{
867
-			logdens[t] = -100; // -INFINITY gives nan's somewhere downstream
868
-		}
869
-		FILE_LOG(logDEBUG4) << "logdens["<<t<<"] = " << logdens[t];
29
+		density[t] = dnorm(this->obs[t], this->mean, this->sd, 0);
870 30
 	}
871 31
 }
872 32
 
873
-void OnlyZeros::calc_densities(double* dens)
33
+void Normal::calc_logdensities(double* logdensity)
874 34
 {
875 35
 	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
876 36
 	for (int t=0; t<this->T; t++)
877 37
 	{
878
-		if(O[t]==0)
879
-		{
880
-			dens[t] = 1.0;
881
-		}
882
-		if(O[t]>0)
883
-		{
884
-			dens[t] = 0.0;
885
-		}
886
-		FILE_LOG(logDEBUG4) << "dens["<<t<<"] = " << dens[t];
887
-	}
888
-}
889
-
890
-void OnlyZeros::copy(Density* other) {}
891
-
892
-double OnlyZeros::getMean()
893
-{
894
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
895
-	return 0;
896
-}
897
-
898
-double OnlyZeros::getVariance()
899
-{
900
-	FILE_LOG(logDEBUG2) << __PRETTY_FUNCTION__;
901
-	return 0;
902
-}
903