-
Notifications
You must be signed in to change notification settings - Fork 0
/
test.cpp
118 lines (101 loc) · 3.48 KB
/
test.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
#include "hmm.h"
#include <math.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#ifndef MAX_MODELS
#define MAX_MODELS 10
#endif
/*
./test MODEL_LIST TEST_DATA RESULT
argv[1] = MODEL_LIST
argv[2] = TEST_DATA
argv[3] = RESULT
argc = 4
Hmm struct{
char *model_name;
int state_num; //number of state
int observ_num; //number of observation
double initial[MAX_STATE]; //initial prob.
double transition[MAX_STATE][MAX_STATE]; //transition prob.
double observation[MAX_OBSERV][MAX_STATE]; //observation prob.
}
*/
double _delta[2][MAX_STATE];
void viterbi_processing(HMM *HMM_models, int number_of_models, char *data, int *best_model_index, double *max_path_prob)
{
int inner_best_model_index = -1;
double inner_max_path_prob = 0.0;
for (int model_index = 0; model_index < number_of_models; model_index++)
{
HMM *model = HMM_models + model_index;
int number_of_state = model->state_num;
int observ = data[0] - 'A';
for (int state = 0; state < number_of_state; state++)
{
_delta[0][state] = model->initial[state] * model->observation[observ][state];
// printf("%f ", _delta[0][state]);
}
// printf("\n");
for (int observT = 1; observT < strlen(data); observT++)
{
int observ = data[observT] - 'A';
for (int state = 0; state < number_of_state; state++)
{
double tmp_high_prob = 0.0;
for (int preState = 0; preState < number_of_state; preState++)
{
double tmp = _delta[0][preState] * model->transition[preState][state];
if (tmp > tmp_high_prob)
{
tmp_high_prob = tmp;
}
}
_delta[1][state] = tmp_high_prob * model->observation[observ][state];
}
for (int state = 0; state < number_of_state; state++)
{
_delta[0][state] = _delta[1][state];
}
}
for (int state = 0; state < number_of_state; state++)
{
if (_delta[1][state] > inner_max_path_prob)
{
inner_max_path_prob = _delta[1][state];
inner_best_model_index = model_index;
}
}
}
*best_model_index = inner_best_model_index;
// printf("%d ", inner_best_model_index + 1);
*max_path_prob = inner_max_path_prob;
// printf("%f\n", inner_max_path_prob);
}
int main(int argc, char *argv[])
{
HMM HMM_models[MAX_MODELS];
int number_of_models = load_models(argv[1], HMM_models, MAX_MODELS);
FILE *input_data = open_or_die(argv[2], "r");
FILE *output_result = open_or_die(argv[3], "w");
FILE *handin = open_or_die(argv[4], "w");
char data[MAX_LINE];
int limit = 0;
while (fscanf(input_data, "%s", data))
{
int best_model_index;
double max_path_prob;
viterbi_processing(HMM_models, number_of_models, data, &best_model_index, &max_path_prob);
// printf("%s %f\n", HMM_models[best_model_index].model_name, max_path_prob);
limit++;
if (limit > 2500)
{
break;
}
fprintf(handin, "%s %e\n", HMM_models[best_model_index].model_name, max_path_prob);
fprintf(output_result, "%s\n", HMM_models[best_model_index].model_name);
}
fclose(input_data);
fclose(output_result);
}