source: trunk/SL/MATRIX/AP_matrix.cxx

Last change on this file was 18634, checked in by westram, 4 years ago
  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 4.7 KB
Line 
1// =============================================================== //
2//                                                                 //
3//   File      : AP_matrix.cxx                                     //
4//   Purpose   :                                                   //
5//                                                                 //
6//   Institute of Microbiology (Technical University Munich)       //
7//   http://www.arb-home.de/                                       //
8//                                                                 //
9// =============================================================== //
10
11#include "AP_matrix.hxx"
12
13#include <arbdbt.h>
14#include <aw_window.hxx>
15#include <aw_root.hxx>
16#include <aw_awar.hxx>
17#include <cfloat>
18
19#define ap_assert(cond) arb_assert(cond)
20
21// ------------------
22//      AP_matrix
23
24AP_matrix::AP_matrix(long si) {
25    ARB_calloc(m, si);
26    for (long i=0; i<si; i++) {
27        ARB_calloc(m[i], si);
28    }
29    size = si;
30}
31
32AP_matrix::~AP_matrix() {
33    for (long i=0; i<size; i++) {
34        free(m[i]);
35    }
36    free(m);
37}
38
39// ---------------------------
40//      AP_userdef_matrix
41
42void AP_userdef_matrix::set_desc(char**& which_desc, int idx, const char *desc) {
43    if (!which_desc) ARB_calloc(which_desc, get_size());
44    which_desc[idx] = strdup(desc);
45}
46
47void AP_userdef_matrix::create_awars(AW_root *awr) {
48    char buffer[1024];
49    int x, y;
50    for (x = 0; x<get_size(); x++) {
51        if (x_description[x]) {
52            for (y = 0; y<get_size(); y++) {
53                if (y_description[y]) {
54                    sprintf(buffer, "%s/B%s/B%s", awar_prefix, x_description[x], y_description[y]);
55                    if (x==y) {
56                        awr->awar_float(buffer, 0)->set_minmax(0.0, 2.0);
57                    }
58                    else {
59                        awr->awar_float(buffer, 1.0)->set_minmax(0.0, 2.0);
60                    }
61                }
62
63            }
64        }
65    }
66}
67void AP_userdef_matrix::update_from_awars(AW_root *awr) {
68    char buffer[1024];
69    int x, y;
70    for (x = 0; x<get_size(); x++) {
71        if (x_description[x]) {
72            for (y = 0; y<get_size(); y++) {
73                if (y_description[y]) {
74                    sprintf(buffer, "%s/B%s/B%s", awar_prefix, x_description[x], y_description[y]);
75                    this->set(x, y, awr->awar(buffer)->read_float());
76                }
77            }
78        }
79    }
80}
81
82void AP_userdef_matrix::create_input_fields(AW_window *aww) {
83    char buffer[1024];
84    int x, y;
85    aww->create_button(NULp, "    ");
86    for (x = 0; x<get_size(); x++) {
87        if (x_description[x]) {
88            aww->create_button(NULp, x_description[x]);
89        }
90    }
91    aww->at_newline();
92    for (x = 0; x<get_size(); x++) {
93        if (x_description[x]) {
94            aww->create_button(NULp, x_description[x]);
95            for (y = 0; y<get_size(); y++) {
96                if (y_description[y]) {
97                    sprintf(buffer, "%s/B%s/B%s", awar_prefix, x_description[x], y_description[y]);
98                    aww->create_input_field(buffer, 4);
99                }
100            }
101            aww->at_newline();
102        }
103    }
104}
105
106void AP_userdef_matrix::normize() { // set values so that average of non diag elems == 1.0
107    int x, y;
108    double sum = 0.0;
109    double elems = 0.0;
110    for (x = 0; x<get_size(); x++) {
111        if (x_description[x]) {
112            for (y = 0; y<get_size(); y++) {
113                if (y!=x && y_description[y]) {
114                    sum += this->get(x, y);
115                    elems += 1.0;
116                }
117            }
118        }
119    }
120    if (sum == 0.0) return;
121    sum /= elems;
122    for (x = 0; x<get_size(); x++) {
123        for (y = 0; y<get_size(); y++) { // LOOP_VECTORIZED
124            this->set(x, y, get(x, y)/sum);
125        }
126    }
127}
128
129AP_userdef_matrix::~AP_userdef_matrix() {
130    for (long i=0; i<get_size(); i++) {
131        if (x_description) free(x_description[i]);
132        if (y_description) free(y_description[i]);
133    }
134    free(x_description);
135    free(y_description);
136    free(awar_prefix);
137}
138
139// --------------------------------------------------------------------------------
140
141#ifdef UNIT_TESTS
142#ifndef TEST_UNIT_H
143#include <test_unit.h>
144#endif
145
146void TEST_AP_smatrix() {
147    // TEST_REJECT(true); // let it fail!
148
149    const int  SIZE = 10;
150    AP_smatrix m(SIZE);
151
152    TEST_EXPECT_EQUAL(m.size(), SIZE);
153    TEST_EXPECT_EQUAL(m.fast_get(9, 8), 0.0);
154
155    for (int i = 0; i<SIZE; ++i) {
156        for (int j = 0; j<=i; ++j) {
157            m.set(i, j, j>0 ? AP_FLOAT(i)/j : i);
158            TEST_EXPECT_EQUAL(m.get(i, j), m.get(j, i));
159        }
160    }
161
162    TEST_EXPECT_EQUAL(m.get_max_value(), 9.0);
163    TEST_EXPECT_EQUAL(m.get(9, 8), 9.0/8.0);
164}
165
166#endif // UNIT_TESTS
167
168// --------------------------------------------------------------------------------
Note: See TracBrowser for help on using the repository browser.