File indexing completed on 2026-05-19 08:08:32
0001
0002
0003 #ifndef _CL_RING_H
0004 #define _CL_RING_H
0005
0006 #include "cln/object.h"
0007 #include "cln/malloc.h"
0008 #include "cln/proplist.h"
0009 #include "cln/number.h"
0010 #include "cln/exception.h"
0011 #include "cln/io.h"
0012
0013 namespace cln {
0014
0015 class cl_I;
0016
0017
0018
0019
0020
0021
0022
0023 class cl_heap_ring;
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045 class cl_ring : public cl_rcpointer {
0046 public:
0047
0048 cl_ring (cl_heap_ring* r);
0049
0050 cl_ring (cl_private_thing);
0051
0052 cl_ring (const cl_ring&);
0053
0054 cl_ring& operator= (const cl_ring&);
0055
0056 cl_ring ();
0057
0058 cl_heap_ring* operator-> () const
0059 { return (cl_heap_ring*)heappointer; }
0060 };
0061 CL_DEFINE_COPY_CONSTRUCTOR2(cl_ring,cl_rcpointer)
0062 CL_DEFINE_ASSIGNMENT_OPERATOR(cl_ring,cl_ring)
0063
0064
0065 inline cl_ring::cl_ring (cl_heap_ring* r)
0066 { cl_inc_pointer_refcount((cl_heap*)r); pointer = r; }
0067
0068 inline cl_ring::cl_ring (cl_private_thing p)
0069 { pointer = p; }
0070
0071 inline bool operator== (const cl_ring& R1, const cl_ring& R2)
0072 { return (R1.pointer == R2.pointer); }
0073 inline bool operator!= (const cl_ring& R1, const cl_ring& R2)
0074 { return (R1.pointer != R2.pointer); }
0075 inline bool operator== (const cl_ring& R1, cl_heap_ring* R2)
0076 { return (R1.pointer == R2); }
0077 inline bool operator!= (const cl_ring& R1, cl_heap_ring* R2)
0078 { return (R1.pointer != R2); }
0079
0080
0081
0082
0083
0084
0085
0086
0087
0088
0089
0090
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105
0106
0107
0108
0109
0110
0111
0112
0113
0114 class _cl_ring_element {
0115 public:
0116 cl_gcobject rep;
0117
0118 _cl_ring_element ();
0119 public:
0120
0121 _cl_ring_element (const cl_heap_ring* R, const cl_gcobject& r) : rep (as_cl_private_thing(r)) { (void)R; }
0122 _cl_ring_element (const cl_ring& R, const cl_gcobject& r) : rep (as_cl_private_thing(r)) { (void)R; }
0123 public:
0124 void* operator new (size_t size) { return malloc_hook(size); }
0125 void* operator new (size_t size, void* ptr) { (void)size; return ptr; }
0126 void operator delete (void* ptr) { free_hook(ptr); }
0127 };
0128
0129 class cl_ring_element : public _cl_ring_element {
0130 protected:
0131 cl_ring _ring;
0132 public:
0133 const cl_ring& ring () const { return _ring; }
0134
0135 cl_ring_element ();
0136 public:
0137
0138 cl_ring_element (const cl_ring& R, const cl_gcobject& r) : _cl_ring_element (R,r), _ring (R) {}
0139 cl_ring_element (const cl_ring& R, const _cl_ring_element& r) : _cl_ring_element (r), _ring (R) {}
0140 public:
0141 void debug_print () const;
0142
0143 void* operator new (size_t size) { return malloc_hook(size); }
0144 void* operator new (size_t size, void* ptr) { (void)size; return ptr; }
0145 void operator delete (void* ptr) { free_hook(ptr); }
0146 };
0147
0148
0149
0150
0151
0152
0153
0154
0155
0156
0157 struct _cl_ring_setops {
0158
0159 void (* fprint) (cl_heap_ring* R, std::ostream& stream, const _cl_ring_element& x);
0160
0161 bool (* equal) (cl_heap_ring* R, const _cl_ring_element& x, const _cl_ring_element& y);
0162
0163 };
0164 struct _cl_ring_addops {
0165
0166 const _cl_ring_element (* zero) (cl_heap_ring* R);
0167 bool (* zerop) (cl_heap_ring* R, const _cl_ring_element& x);
0168
0169 const _cl_ring_element (* plus) (cl_heap_ring* R, const _cl_ring_element& x, const _cl_ring_element& y);
0170
0171 const _cl_ring_element (* minus) (cl_heap_ring* R, const _cl_ring_element& x, const _cl_ring_element& y);
0172
0173 const _cl_ring_element (* uminus) (cl_heap_ring* R, const _cl_ring_element& x);
0174
0175 };
0176 struct _cl_ring_mulops {
0177
0178 const _cl_ring_element (* one) (cl_heap_ring* R);
0179
0180 const _cl_ring_element (* canonhom) (cl_heap_ring* R, const cl_I& x);
0181
0182 const _cl_ring_element (* mul) (cl_heap_ring* R, const _cl_ring_element& x, const _cl_ring_element& y);
0183
0184 const _cl_ring_element (* square) (cl_heap_ring* R, const _cl_ring_element& x);
0185
0186 const _cl_ring_element (* expt_pos) (cl_heap_ring* R, const _cl_ring_element& x, const cl_I& y);
0187
0188 };
0189 typedef const _cl_ring_setops cl_ring_setops;
0190 typedef const _cl_ring_addops cl_ring_addops;
0191 typedef const _cl_ring_mulops cl_ring_mulops;
0192
0193
0194
0195 class cl_heap_ring : public cl_heap {
0196 public:
0197
0198 void* operator new (size_t size) { return malloc_hook(size); }
0199
0200 void operator delete (void* ptr) { free_hook(ptr); }
0201 private:
0202 cl_property_list properties;
0203 protected:
0204 cl_ring_setops* setops;
0205 cl_ring_addops* addops;
0206 cl_ring_mulops* mulops;
0207 public:
0208
0209
0210 public:
0211
0212 void _fprint (std::ostream& stream, const _cl_ring_element& x)
0213 { setops->fprint(this,stream,x); }
0214 bool _equal (const _cl_ring_element& x, const _cl_ring_element& y)
0215 { return setops->equal(this,x,y); }
0216 const _cl_ring_element _zero ()
0217 { return addops->zero(this); }
0218 bool _zerop (const _cl_ring_element& x)
0219 { return addops->zerop(this,x); }
0220 const _cl_ring_element _plus (const _cl_ring_element& x, const _cl_ring_element& y)
0221 { return addops->plus(this,x,y); }
0222 const _cl_ring_element _minus (const _cl_ring_element& x, const _cl_ring_element& y)
0223 { return addops->minus(this,x,y); }
0224 const _cl_ring_element _uminus (const _cl_ring_element& x)
0225 { return addops->uminus(this,x); }
0226 const _cl_ring_element _one ()
0227 { return mulops->one(this); }
0228 const _cl_ring_element _canonhom (const cl_I& x)
0229 { return mulops->canonhom(this,x); }
0230 const _cl_ring_element _mul (const _cl_ring_element& x, const _cl_ring_element& y)
0231 { return mulops->mul(this,x,y); }
0232 const _cl_ring_element _square (const _cl_ring_element& x)
0233 { return mulops->square(this,x); }
0234 const _cl_ring_element _expt_pos (const _cl_ring_element& x, const cl_I& y)
0235 { return mulops->expt_pos(this,x,y); }
0236
0237 void fprint (std::ostream& stream, const cl_ring_element& x)
0238 {
0239 if (!(x.ring() == this)) throw runtime_exception();
0240 _fprint(stream,x);
0241 }
0242 bool equal (const cl_ring_element& x, const cl_ring_element& y)
0243 {
0244 if (!(x.ring() == this)) throw runtime_exception();
0245 if (!(y.ring() == this)) throw runtime_exception();
0246 return _equal(x,y);
0247 }
0248 const cl_ring_element zero ()
0249 {
0250 return cl_ring_element(this,_zero());
0251 }
0252 bool zerop (const cl_ring_element& x)
0253 {
0254 if (!(x.ring() == this)) throw runtime_exception();
0255 return _zerop(x);
0256 }
0257 const cl_ring_element plus (const cl_ring_element& x, const cl_ring_element& y)
0258 {
0259 if (!(x.ring() == this)) throw runtime_exception();
0260 if (!(y.ring() == this)) throw runtime_exception();
0261 return cl_ring_element(this,_plus(x,y));
0262 }
0263 const cl_ring_element minus (const cl_ring_element& x, const cl_ring_element& y)
0264 {
0265 if (!(x.ring() == this)) throw runtime_exception();
0266 if (!(y.ring() == this)) throw runtime_exception();
0267 return cl_ring_element(this,_minus(x,y));
0268 }
0269 const cl_ring_element uminus (const cl_ring_element& x)
0270 {
0271 if (!(x.ring() == this)) throw runtime_exception();
0272 return cl_ring_element(this,_uminus(x));
0273 }
0274 const cl_ring_element one ()
0275 {
0276 return cl_ring_element(this,_one());
0277 }
0278 const cl_ring_element canonhom (const cl_I& x)
0279 {
0280 return cl_ring_element(this,_canonhom(x));
0281 }
0282 const cl_ring_element mul (const cl_ring_element& x, const cl_ring_element& y)
0283 {
0284 if (!(x.ring() == this)) throw runtime_exception();
0285 if (!(y.ring() == this)) throw runtime_exception();
0286 return cl_ring_element(this,_mul(x,y));
0287 }
0288 const cl_ring_element square (const cl_ring_element& x)
0289 {
0290 if (!(x.ring() == this)) throw runtime_exception();
0291 return cl_ring_element(this,_square(x));
0292 }
0293 const cl_ring_element expt_pos (const cl_ring_element& x, const cl_I& y)
0294 {
0295 if (!(x.ring() == this)) throw runtime_exception();
0296 return cl_ring_element(this,_expt_pos(x,y));
0297 }
0298
0299 cl_property* get_property (const cl_symbol& key)
0300 { return properties.get_property(key); }
0301 void add_property (cl_property* new_property)
0302 { properties.add_property(new_property); }
0303
0304 cl_heap_ring (cl_ring_setops* setopv, cl_ring_addops* addopv, cl_ring_mulops* mulopv)
0305 : setops (setopv), addops (addopv), mulops (mulopv)
0306 { refcount = 0; }
0307 };
0308 #define SUBCLASS_cl_heap_ring() \
0309 public: \
0310 \
0311 void* operator new (size_t size) { return malloc_hook(size); } \
0312 \
0313 void operator delete (void* ptr) { free_hook(ptr); }
0314
0315
0316
0317
0318 inline void fprint (std::ostream& stream, const cl_ring_element& x)
0319 { x.ring()->fprint(stream,x); }
0320 CL_DEFINE_PRINT_OPERATOR(cl_ring_element)
0321
0322
0323 inline const cl_ring_element operator+ (const cl_ring_element& x, const cl_ring_element& y)
0324 { return x.ring()->plus(x,y); }
0325
0326
0327 inline const cl_ring_element operator- (const cl_ring_element& x)
0328 { return x.ring()->uminus(x); }
0329
0330
0331 inline const cl_ring_element operator- (const cl_ring_element& x, const cl_ring_element& y)
0332 { return x.ring()->minus(x,y); }
0333
0334
0335 inline bool operator== (const cl_ring_element& x, const cl_ring_element& y)
0336 { return x.ring()->equal(x,y); }
0337 inline bool operator!= (const cl_ring_element& x, const cl_ring_element& y)
0338 { return !x.ring()->equal(x,y); }
0339
0340
0341 inline bool zerop (const cl_ring_element& x)
0342 { return x.ring()->zerop(x); }
0343
0344
0345 inline const cl_ring_element operator* (const cl_ring_element& x, const cl_ring_element& y)
0346 { return x.ring()->mul(x,y); }
0347
0348
0349 inline const cl_ring_element square (const cl_ring_element& x)
0350 { return x.ring()->square(x); }
0351
0352
0353 inline const cl_ring_element expt_pos (const cl_ring_element& x, const cl_I& y)
0354 { return x.ring()->expt_pos(x,y); }
0355
0356
0357
0358
0359
0360 inline const cl_ring_element operator* (const cl_I& x, const cl_ring_element& y)
0361 { return y.ring()->mul(y.ring()->canonhom(x),y); }
0362 inline const cl_ring_element operator* (const cl_ring_element& x, const cl_I& y)
0363 { return x.ring()->mul(x.ring()->canonhom(y),x); }
0364
0365
0366
0367
0368
0369
0370 class uninitialized_ring_exception : public runtime_exception {
0371 public:
0372 uninitialized_ring_exception ();
0373 };
0374
0375
0376 class uninitialized_exception : public runtime_exception {
0377 public:
0378 explicit uninitialized_exception (const _cl_ring_element& obj);
0379 uninitialized_exception (const _cl_ring_element& obj_x, const _cl_ring_element& obj_y);
0380 };
0381
0382 extern const cl_ring cl_no_ring;
0383 extern cl_class cl_class_no_ring;
0384
0385 class cl_no_ring_init_helper
0386 {
0387 static int count;
0388 public:
0389 cl_no_ring_init_helper();
0390 ~cl_no_ring_init_helper();
0391 };
0392 static cl_no_ring_init_helper cl_no_ring_init_helper_instance;
0393
0394 inline cl_ring::cl_ring ()
0395 : cl_rcpointer (as_cl_private_thing(cl_no_ring)) {}
0396 inline _cl_ring_element::_cl_ring_element ()
0397 : rep ((cl_private_thing) cl_combine(cl_FN_tag,0)) {}
0398 inline cl_ring_element::cl_ring_element ()
0399 : _cl_ring_element (), _ring () {}
0400
0401
0402
0403
0404
0405 template <class T>
0406 struct cl_number_ring_ops {
0407 bool (* contains) (const cl_number&);
0408 bool (* equal) (const T&, const T&);
0409 bool (* zerop) (const T&);
0410 const T (* plus) (const T&, const T&);
0411 const T (* minus) (const T&, const T&);
0412 const T (* uminus) (const T&);
0413 const T (* mul) (const T&, const T&);
0414 const T (* square) (const T&);
0415 const T (* expt_pos) (const T&, const cl_I&);
0416 };
0417 class cl_heap_number_ring : public cl_heap_ring {
0418 public:
0419 cl_number_ring_ops<cl_number>* ops;
0420
0421 cl_heap_number_ring (cl_ring_setops* setopv, cl_ring_addops* addopv, cl_ring_mulops* mulopv, cl_number_ring_ops<cl_number>* opv)
0422 : cl_heap_ring (setopv,addopv,mulopv), ops (opv) {}
0423 };
0424
0425 class cl_number_ring : public cl_ring {
0426 public:
0427 cl_number_ring (cl_heap_number_ring* r)
0428 : cl_ring (r) {}
0429 };
0430
0431 template <class T>
0432 class cl_specialized_number_ring : public cl_number_ring {
0433 public:
0434 cl_specialized_number_ring ();
0435 };
0436
0437
0438 inline bool instanceof (const cl_number& x, const cl_number_ring& R)
0439 {
0440 return ((cl_heap_number_ring*) R.heappointer)->ops->contains(x);
0441 }
0442
0443
0444
0445
0446
0447
0448 #define The(type) *(const type *) & cl_identity
0449 #define The2(type) *(const type *) & cl_identity2
0450
0451 inline const cl_ring& cl_identity (const cl_ring& r) { return r; }
0452 inline const cl_ring_element& cl_identity2 (const cl_ring_element& x) { return x; }
0453 inline const cl_gcobject& cl_identity (const _cl_ring_element& x) { return x.rep; }
0454
0455
0456
0457 #ifdef CL_DEBUG
0458 extern int cl_ring_debug_module;
0459 CL_FORCE_LINK(cl_ring_debug_dummy, cl_ring_debug_module)
0460 #endif
0461
0462 }
0463
0464 #endif