-
Notifications
You must be signed in to change notification settings - Fork 11
/
ca_vec.h
212 lines (167 loc) · 4.98 KB
/
ca_vec.h
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
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
/*
Copyright (C) 2020 Fredrik Johansson
This file is part of Calcium.
Calcium is free software: you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 2.1 of the License, or
(at your option) any later version. See <http://www.gnu.org/licenses/>.
*/
#ifndef CA_VEC_H
#define CA_VEC_H
#ifdef CA_VEC_INLINES_C
#define CA_VEC_INLINE
#else
#define CA_VEC_INLINE static __inline__
#endif
#include <stdio.h>
#include "flint/flint.h"
#include "flint/fmpz_poly.h"
#include "flint/fmpq_poly.h"
#include "arb_poly.h"
#include "acb_poly.h"
#include "antic/nf.h"
#include "antic/nf_elem.h"
#include "ca.h"
#ifdef __cplusplus
extern "C" {
#endif
/* Vector object */
typedef struct
{
ca_ptr entries;
slong alloc;
slong length;
}
ca_vec_struct;
typedef ca_vec_struct ca_vec_t[1];
#define ca_vec_entry(vec, i) ((vec)->entries + (i))
CA_VEC_INLINE ca_ptr
ca_vec_entry_ptr(ca_vec_t vec, slong i)
{
return ca_vec_entry(vec, i);
}
/* Memory management */
ca_ptr _ca_vec_init(slong len, ca_ctx_t ctx);
void ca_vec_init(ca_vec_t vec, slong len, ca_ctx_t ctx);
void _ca_vec_clear(ca_ptr v, slong len, ca_ctx_t ctx);
void ca_vec_clear(ca_vec_t vec, ca_ctx_t ctx);
void _ca_vec_swap(ca_ptr vec1, ca_ptr vec2, slong len, ca_ctx_t ctx);
CA_VEC_INLINE void
ca_vec_swap(ca_vec_t vec1, ca_vec_t vec2, ca_ctx_t ctx)
{
ca_vec_struct t = *vec1;
*vec1 = *vec2;
*vec2 = t;
}
/* Length */
CA_VEC_INLINE
slong ca_vec_length(const ca_vec_t vec, ca_ctx_t ctx)
{
return vec->length;
}
void _ca_vec_fit_length(ca_vec_t vec, slong len, ca_ctx_t ctx);
void ca_vec_set_length(ca_vec_t res, slong len, ca_ctx_t ctx);
/* Assignment */
void _ca_vec_set(ca_ptr res, ca_srcptr src, slong len, ca_ctx_t ctx);
void ca_vec_set(ca_vec_t res, const ca_vec_t src, ca_ctx_t ctx);
/* Special vectors */
void _ca_vec_zero(ca_ptr res, slong len, ca_ctx_t ctx);
void ca_vec_zero(ca_vec_t res, slong len, ca_ctx_t ctx);
CA_VEC_INLINE
void _ca_vec_unknown(ca_ptr vec, slong len, ca_ctx_t ctx)
{
slong i;
for (i = 0; i < len; i++)
ca_unknown(vec + i, ctx);
}
CA_VEC_INLINE
void _ca_vec_undefined(ca_ptr vec, slong len, ca_ctx_t ctx)
{
slong i;
for (i = 0; i < len; i++)
ca_undefined(vec + i, ctx);
}
/* Input and output */
void ca_vec_print(const ca_vec_t vec, ca_ctx_t ctx);
void ca_vec_printn(const ca_vec_t vec, slong digits, ca_ctx_t ctx);
/* List operations */
CA_VEC_INLINE void
ca_vec_append(ca_vec_t vec, const ca_t f, ca_ctx_t ctx)
{
_ca_vec_fit_length(vec, vec->length + 1, ctx);
ca_set(vec->entries + vec->length, f, ctx);
vec->length++;
}
/* Arithmetic */
void _ca_vec_neg(ca_ptr res, ca_srcptr src, slong len, ca_ctx_t ctx);
void ca_vec_neg(ca_vec_t res, const ca_vec_t src, ca_ctx_t ctx);
void _ca_vec_add(ca_ptr res, ca_srcptr vec1, ca_srcptr vec2, slong len, ca_ctx_t ctx);
void _ca_vec_sub(ca_ptr res, ca_srcptr vec1, ca_srcptr vec2, slong len, ca_ctx_t ctx);
void _ca_vec_scalar_mul_ca(ca_ptr res, ca_srcptr src, slong len, const ca_t c, ca_ctx_t ctx);
void _ca_vec_scalar_div_ca(ca_ptr res, ca_srcptr src, slong len, const ca_t c, ca_ctx_t ctx);
void _ca_vec_scalar_addmul_ca(ca_ptr res, ca_srcptr vec, slong len, const ca_t c, ca_ctx_t ctx);
void _ca_vec_scalar_submul_ca(ca_ptr res, ca_srcptr vec, slong len, const ca_t c, ca_ctx_t ctx);
/* Comparisons and predicates */
truth_t _ca_vec_check_is_zero(ca_srcptr vec, slong len, ca_ctx_t ctx);
/* Internal representation */
CA_VEC_INLINE int
_ca_vec_is_fmpq_vec(ca_srcptr vec, slong len, ca_ctx_t ctx)
{
slong i;
for (i = 0; i < len; i++)
if (!CA_IS_QQ(vec + i, ctx))
return 0;
return 1;
}
CA_VEC_INLINE int
_ca_vec_fmpq_vec_is_fmpz_vec(ca_srcptr vec, slong len, ca_ctx_t ctx)
{
slong i;
for (i = 0; i < len; i++)
if (!fmpz_is_one(CA_FMPQ_DENREF(vec + i)))
return 0;
return 1;
}
CA_VEC_INLINE void
_ca_vec_fmpq_vec_get_fmpz_vec_den(fmpz * c, fmpz_t den, ca_srcptr vec, slong len, ca_ctx_t ctx)
{
slong i;
fmpz_one(den);
if (_ca_vec_fmpq_vec_is_fmpz_vec(vec, len, ctx))
{
for (i = 0; i < len; i++)
fmpz_set(c + i, CA_FMPQ_NUMREF(vec + i));
}
else
{
for (i = 0; i < len; i++)
fmpz_lcm(den, den, CA_FMPQ_DENREF(vec + i));
for (i = 0; i < len; i++)
{
fmpz_divexact(c + i, den, CA_FMPQ_DENREF(vec + i));
fmpz_mul(c + i, c + i, CA_FMPQ_NUMREF(vec + i));
}
}
}
CA_VEC_INLINE void
_ca_vec_set_fmpz_vec_div_fmpz(ca_ptr res, const fmpz * v, const fmpz_t den, slong len, ca_ctx_t ctx)
{
slong i;
if (fmpz_is_one(den))
{
for (i = 0; i < len; i++)
ca_set_fmpz(res + i, v + i, ctx);
}
else
{
for (i = 0; i < len; i++)
{
ca_set_fmpz(res + i, v + i, ctx); /* todo: optimize */
ca_div_fmpz(res + i, res + i, den, ctx);
}
}
}
#ifdef __cplusplus
}
#endif
#endif