Compare commits

...

323 commits

Author SHA1 Message Date
b03e35d422 Merge pull request 'update workflows' (#10) from fix into main
All checks were successful
ci/woodpecker/manual/woodpecker Pipeline was successful
Reviewed-on: #10
2024-05-17 20:33:15 +02:00
Christian Zimmermann
a1a1448ee6 update workflows 2024-05-17 20:31:37 +02:00
0139fd1192 Merge pull request 'base/utils.h: add algorithm library (seems to be neccessary on newer systems)' (#9) from fix into main
All checks were successful
ci/woodpecker/manual/woodpecker Pipeline was successful
Reviewed-on: #9
2024-05-16 18:40:45 +02:00
Christian Zimmermann
ecd279e5b7 base/utils.h: add algorithm library (seems to be neccessary on newer systems) 2024-05-15 18:11:38 +02:00
27c4c59d19 Merge pull request 'correct .github/workflows/main.yml' (#8) from dev into main
Reviewed-on: #8
2024-02-04 18:57:01 +00:00
Christian Zimmermann
a68ed3722f correct .github/workflows/main.yml 2024-02-04 19:56:40 +01:00
1d36fefec4 Merge pull request 'correct .github/workflows/main.yml' (#7) from dev into main
Reviewed-on: #7
2024-02-04 18:53:35 +00:00
Christian Zimmermann
cc332069ad correct .github/workflows/main.yml 2024-02-04 19:53:16 +01:00
38d0258aa4 Merge pull request 'correct .github/workflows/main.yml' (#6) from dev into main
Reviewed-on: #6
2024-02-04 18:34:06 +00:00
Christian Zimmermann
1aa6828e8a correct .github/workflows/main.yml 2024-02-04 19:33:43 +01:00
e0b32d7e25 Merge pull request 'github doxy task: workflow_dispatch' (#5) from dev into main
Reviewed-on: #5
2024-02-04 18:31:34 +00:00
Christian Zimmermann
29913bb350 github doxy task: workflow_dispatch 2024-02-04 19:31:07 +01:00
75b2bde675 Merge pull request 'add github doxygen workflow + add LICENSE + update README' (#4) from dev into main
Reviewed-on: #4
2024-02-04 18:14:48 +00:00
Christian Zimmermann
b802aac2d0 add github doxygen workflow + add LICENSE + update README
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-04 19:05:12 +01:00
e392db5fdc Merge pull request 'dev' (#3) from dev into main
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
Reviewed-on: chizeta/CNORXZ#3
2024-02-03 23:49:58 +00:00
Christian Zimmermann
9b9a8a596e update TODO
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
ci/woodpecker/pr/woodpecker Pipeline was successful
ci/woodpecker/pull_request_closed/woodpecker Pipeline was successful
2024-02-04 00:39:28 +01:00
Christian Zimmermann
1261435835 correct CMakeLists.txt
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-04 00:26:28 +01:00
Christian Zimmermann
be312c31bb readme minor changes...
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 23:55:54 +01:00
Christian Zimmermann
b20de211ef remove some code that has been already commented out
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 23:35:29 +01:00
Christian Zimmermann
8a0fdf7a7c improve comment notation + add missing briefs
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 23:21:40 +01:00
Christian Zimmermann
c478bf0fae more documentation + clean up
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 22:02:01 +01:00
Christian Zimmermann
5eff4cfe3f improve doxygen setup
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 18:35:13 +01:00
Christian Zimmermann
871910355d cereal documentation
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 16:44:34 +01:00
Christian Zimmermann
b2c52384b0 README: expressions and operations section (WIP)
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-03 01:22:52 +01:00
6793fc1bdb Merge pull request 'dev' (#2) from dev into main
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
Reviewed-on: chizeta/CNORXZ#2
2024-02-02 19:36:53 +00:00
Christian Zimmermann
1a26f1407f remove deprecated definition in .woodpecker.yml
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
ci/woodpecker/pr/woodpecker Pipeline was successful
ci/woodpecker/pull_request_closed/woodpecker Pipeline was successful
2024-02-02 20:31:50 +01:00
Christian Zimmermann
dc7137f400 hdf5: fix oinfo bug occuring for older hdf5 versions
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-02-02 20:28:22 +01:00
Christian Zimmermann
2023d64a5f hdf5: clean up + fixes
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-02 19:25:09 +01:00
Christian Zimmermann
190032729a urange: fix bug (seg fault) in getMeta
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-02 16:27:18 +01:00
Christian Zimmermann
27466f6ef1 hdf5: fix doxy errors + remove some unused code
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-02 15:11:03 +01:00
Christian Zimmermann
c46d9b1772 hdf5: virtual function exists() in ContentBase + hdf5 header documentation
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-02-02 14:51:51 +01:00
Christian Zimmermann
1f7ebae61b WIP: hdf5 documentation
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-02 12:13:54 +01:00
Christian Zimmermann
26831adb94 fix compile error
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-02-02 11:55:27 +01:00
Christian Zimmermann
be3f5521e8 WIP: hdf5 documentation
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-02-02 00:36:14 +01:00
Christian Zimmermann
eb3055ddca hdf5: several fixes + yrange: add setSub member function + dindex: add missing operator*(dindex,index)
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-02-01 18:22:08 +01:00
Christian Zimmermann
6f3601daa4 hdf5: dataset
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-02-01 00:11:20 +01:00
Christian Zimmermann
e2e233b931 im com
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-31 19:09:04 +01:00
Christian Zimmermann
df228d545b WIP: hdf5: Dataset
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-31 00:16:34 +01:00
Christian Zimmermann
84f18e1d5e hdf5: groups: handle paths to access sub-content objects
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-30 19:18:33 +01:00
Christian Zimmermann
39c0a3146f hdf5: table: iterRecords + test
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-30 01:13:58 +01:00
Christian Zimmermann
f7c00eab8c improve table read / readRecord
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-30 00:14:06 +01:00
Christian Zimmermann
e3ad04e56c add table read functions
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-28 23:39:27 +01:00
Christian Zimmermann
b2637802be changes in STable
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-28 16:42:11 +01:00
Christian Zimmermann
30a3c0b756 fixes in to_string + h5 attributes
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-28 01:57:52 +01:00
Christian Zimmermann
035ae78785 h5: simple attribute handling (to be tested)
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-25 01:19:26 +01:00
Christian Zimmermann
d5b42c9c00 hdf5: group iterations
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-23 02:17:56 +01:00
Christian Zimmermann
f77132ddfe hdf5: fix group mkCont + improve error handling of urange/yrange at()
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2024-01-22 00:03:08 +01:00
Christian Zimmermann
0bfee171e0 add POpRoot class + prange: implement xpr()
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-20 22:38:15 +01:00
Christian Zimmermann
91f9a3c957 prange: add missing extend() implementation
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-20 21:33:40 +01:00
Christian Zimmermann
21a11eb4f6 ranges: add remaining doxy comments
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-19 23:32:41 +01:00
Christian Zimmermann
a5031d80b1 prange comments
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-17 22:57:18 +01:00
Christian Zimmermann
ac352206c7 more doc
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-14 23:57:42 +01:00
Christian Zimmermann
4c71fac091 more documentation; WIP: mrange doc
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-13 18:26:28 +01:00
Christian Zimmermann
0eb505f41b yrange: solve lower-dim-reformat issue
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-03 19:18:20 +01:00
Christian Zimmermann
d66164e874 mrange: solve lower-dim-reformat issue
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-03 11:54:06 +01:00
Christian Zimmermann
ab13d97b03 cmake: new version string
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2024-01-02 20:43:05 +01:00
Christian Zimmermann
e3f8fa17ba yrange/yindex: comments
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-30 18:10:07 +01:00
f6af00d162 Merge pull request 'dev' (#1) from dev into main
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
Reviewed-on: chizeta/CNORXZ#1
2023-12-29 23:37:24 +00:00
Christian Zimmermann
671eedf9fe link logo in html docu
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
ci/woodpecker/pr/woodpecker Pipeline was successful
ci/woodpecker/pull_request_closed/woodpecker Pipeline was successful
2023-12-30 00:27:54 +01:00
Christian Zimmermann
30a6acf903 readme: include logo
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-30 00:23:06 +01:00
Christian Zimmermann
7376905928 doxy: use readme as main page
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-30 00:09:29 +01:00
Christian Zimmermann
e8db02a6ec more doc
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-29 22:48:28 +01:00
Christian Zimmermann
5a75c7964f remove .gitlab-ci.yml
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-29 15:20:02 +01:00
Christian Zimmermann
6857e3fc7d yindex+mindex: reformat: todo errmsg
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-29 00:36:52 +01:00
Christian Zimmermann
e94bad17fb ... and again...
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-12-28 23:14:07 +01:00
Christian Zimmermann
2155568864 CI: scalar build
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-28 23:12:04 +01:00
Christian Zimmermann
ab4cb78258 WIP: index format
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-28 21:57:05 +01:00
Christian Zimmermann
c72fbc329d WIP: index format test + fixes...
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-28 00:25:44 +01:00
Christian Zimmermann
bf83c26a12 index reformat: apply format change to same instance (no copy)
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-25 22:07:39 +01:00
Christian Zimmermann
62b75c01a0 WIP: reformat tests
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-25 15:08:40 +01:00
Christian Zimmermann
df2a8e5a0b WIP: index reformat: mindex: do not copy single-indices
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-22 01:52:49 +01:00
Christian Zimmermann
4b9c8e94dc WIP: index reformat
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-19 18:43:05 +01:00
Christian Zimmermann
00eb2d2fb1 WIP: reformat
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-19 02:08:15 +01:00
Christian Zimmermann
642381ecc0 YRange: bug fix in deepFormat + add setFormat + array: bug fix in check format
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-11 02:20:02 +01:00
Christian Zimmermann
fb8a44e88b WIP: todos in array operator(), operator[]
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-11 01:11:49 +01:00
Christian Zimmermann
a7c1aad6fc comment memory section
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-10 18:59:09 +01:00
Christian Zimmermann
129c27a28d index: remove xpr() from base type + add trait to check if expression is available
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-12-02 18:02:34 +01:00
Christian Zimmermann
eee1805f88 get intrinsics vector size from environment + compile with avx -> works
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-11-20 00:41:37 +01:00
Christian Zimmermann
886c47bc24 add TODOs
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-19 19:52:46 +01:00
Christian Zimmermann
55ebc2e3d7 finish xpr_base.cc.h
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-19 19:17:55 +01:00
Christian Zimmermann
a5593a04f6 comment-out empty vpos specialization (might have been deprecated before, TDOD: check)
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-19 18:43:42 +01:00
Christian Zimmermann
3b7040447c re-implement DIndex ifor (-> template)
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-12 23:16:56 +01:00
Christian Zimmermann
0f0a01793c for return value -> None
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-09 22:53:35 +01:00
Christian Zimmermann
43f5e560fa dynamic indices: DXpr<SizeT> -> DXpr<None>
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-08 02:06:16 +01:00
Christian Zimmermann
09f15408b1 for: bug fix
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-07 02:22:30 +01:00
Christian Zimmermann
3d08dc530e implement missing trivial format checks
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-06 23:21:03 +01:00
Christian Zimmermann
be44541135 more doxy comments + WIP: index member function formatIsTrivial
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-05 22:20:12 +01:00
Christian Zimmermann
7487929bfc add comment header to include/array files
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-05 16:27:36 +01:00
Christian Zimmermann
c055ef39da base+ranges: more docu
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-05 01:25:23 +01:00
Christian Zimmermann
62f83de07b add more docu for range_base / index_base code
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-04 02:12:32 +01:00
Christian Zimmermann
337774cd8f ranges: comment blocks
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-04 00:24:30 +01:00
Christian Zimmermann
c9f7407de8 WIP: doxygen + remove unused code
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-03 02:01:01 +01:00
Christian Zimmermann
17d40add98 rewrite README, wip
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-11-01 18:50:04 +01:00
Christian Zimmermann
fcf6712912 WIP: doxy
All checks were successful
ci/woodpecker/manual/woodpecker Pipeline was successful
2023-11-01 02:58:05 +01:00
Christian Zimmermann
636c1d6407 corrections + remove old files + some todos 2023-11-01 01:23:32 +01:00
Christian Zimmermann
0e616f8370 add operator- Index 2023-10-29 22:03:45 +01:00
Christian Zimmermann
04af9ec3e8 remove old code (access.h + access.cc.h) 2023-10-29 19:20:26 +01:00
Christian Zimmermann
cb2db9c80d add first slice tests + corresp fixes 2023-10-24 02:01:29 +02:00
Christian Zimmermann
2a763d67be test prange of prange + corresp fixes 2023-10-22 17:06:30 +02:00
Christian Zimmermann
eb5276c967 tests and fix bugs regarding prange 2023-10-22 01:33:54 +02:00
Christian Zimmermann
cf0e7c5856 implement missing prange member functions 2023-10-21 19:23:38 +02:00
Christian Zimmermann
301967288f index: add prange member function 2023-10-21 18:29:16 +02:00
Christian Zimmermann
db6b0a14ec WIP: slicing + partial ranges
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-09-18 00:01:27 +02:00
Christian Zimmermann
9b706c4ec0 check format compatibility
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-10 14:35:53 +02:00
Christian Zimmermann
bfeda55904 WIP: check format compatibility
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-09 13:20:20 +02:00
Christian Zimmermann
303450d068 WIP: deepFormat + check format compatibility
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-09 12:56:39 +02:00
Christian Zimmermann
7e182ded83 comment out formatFrom/slice ...
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-09 11:29:22 +02:00
Christian Zimmermann
944db31e02 WIP: deepFormat + check format compatibility
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-09 11:14:03 +02:00
Christian Zimmermann
b0a5b1d13f WIP: deepFormat + check format compatibility
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-09-08 19:18:54 +02:00
Christian Zimmermann
1eea0e8a3f fix again .woodpecker.yml
All checks were successful
ci/woodpecker/push/woodpecker Pipeline was successful
2023-09-06 17:04:05 +02:00
Christian Zimmermann
81a21120ed fix compile errors
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-09-06 17:01:59 +02:00
Christian Zimmermann
5acd80bdcb try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 13:17:24 +02:00
Christian Zimmermann
425a5524c4 try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 13:16:56 +02:00
Christian Zimmermann
b0810b80b7 try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:55:12 +02:00
Christian Zimmermann
28e14e1604 debug CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:51:20 +02:00
Christian Zimmermann
babf17cf6f try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:50:29 +02:00
Christian Zimmermann
98c168cbf3 debug CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:30:46 +02:00
Christian Zimmermann
44ba32b029 try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:29:06 +02:00
Christian Zimmermann
defa7c9211 try to fix CMakeLists.txt
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:27:28 +02:00
Christian Zimmermann
b5be793548 remove tabs in .woodpecker.yml
Some checks failed
ci/woodpecker/push/woodpecker Pipeline failed
2023-08-31 12:15:45 +02:00
Christian Zimmermann
9d9180fdcb add .woodpecker.yml 2023-08-31 12:12:52 +02:00
Christian Zimmermann
cf5fabd04b im com 2023-08-31 12:07:20 +02:00
Christian Zimmermann
f1b1298c69 reformat -> formatTo/formatFrom 2023-06-25 23:35:09 +02:00
Christian Zimmermann
f088ba156b remove special assignment operator in Consecutive (appeared to be unneccesary) 2023-06-18 02:49:43 +02:00
Christian Zimmermann
17b8b79ade various fixes regarding usage of Consecutive 2023-06-17 21:51:37 +02:00
Christian Zimmermann
bd6f15156b WIP: fix test errors... 2023-06-15 00:41:17 +02:00
Christian Zimmermann
717e4a6548 WIP: fix compile errors regarding first extension operation test 2023-06-12 00:00:20 +02:00
Christian Zimmermann
1919d373df indices: fullfill missing iterator requirements 2023-06-11 22:28:10 +02:00
Christian Zimmermann
811e955491 WIP: EIndex tests 2023-06-11 03:06:30 +02:00
Christian Zimmermann
59a9236c04 rename index.format(index) -> index.reformat(index) (because of conflicting member function names) 2023-06-04 23:11:46 +02:00
Christian Zimmermann
ba02601b97 EIndex: new inheritance structure: SIndex<S> -> LIndex<SIndex<S>,L> -> EIndex<S,L> 2023-06-04 22:14:26 +02:00
Christian Zimmermann
52517675a5 EFor: F argument 2023-06-04 17:31:47 +02:00
Christian Zimmermann
e9fde3d900 srange casts + add first eindex implementation 2023-05-29 23:05:47 +02:00
Christian Zimmermann
3f8c7aacc3 srange.cc.h (casts missing...) 2023-05-29 17:41:55 +02:00
Christian Zimmermann
3c98377e2d add srange.h 2023-05-27 20:03:41 +02:00
Christian Zimmermann
1610084abd Merge branch 'dev' of git.f3l.de:chizeta/cnorxz into dev 2023-05-10 01:20:40 +02:00
Christian Zimmermann
0593150651 add cereal write/readFile wrappers 2023-05-10 01:20:31 +02:00
Christian Zimmermann
cceace2ef0 minor change in CMakeLists.txt + fix preprocessor variables to prevent extra semicolon error 2023-05-09 16:22:25 +02:00
Christian Zimmermann
7ea21da81a ranges: add sub() to ranges -> returns MArray of RangePtrs 2023-05-07 21:46:46 +02:00
Christian Zimmermann
862697edef include/base/types.h: include <cstdint> 2023-05-07 17:53:49 +02:00
Christian Zimmermann
ef45d8cbac ranges: add some of the possible casts for URange 2023-05-05 19:29:10 +02:00
Christian Zimmermann
026c7f1a87 add missing operator* for GMIndex + fix various bugs 2023-03-19 01:48:51 +01:00
Christian Zimmermann
4642ebe6d2 various fixes 2023-03-15 17:29:24 +01:00
Christian Zimmermann
c1f92b4685 prange.cc.h: add missing template argument 2023-03-15 13:45:37 +01:00
Christian Zimmermann
40a86441cb add missing PRange / PRangeFactory member implementations 2023-03-15 12:20:48 +01:00
Christian Zimmermann
0e1ec2e95a include prange + fix corresponding compile errors (untested) 2023-03-15 11:46:21 +01:00
Christian Zimmermann
2d4d0b8ee9 change behavior of operator* for RangePtr: preserve sub-range structure 2023-03-14 19:07:05 +01:00
Christian Zimmermann
1d6f8dc52b try to fix pipeline 2023-03-12 16:54:32 +01:00
Christian Zimmermann
bea9add008 mrange: range cast 2023-03-12 04:30:42 +01:00
Christian Zimmermann
abb47cbb06 array base: add using CAB::operator() 2023-03-08 20:03:19 +01:00
Christian Zimmermann
b77955a36e op roots: index pos offset (only valid for non-looped indices) 2023-03-08 02:08:30 +01:00
Christian Zimmermann
2864c10056 various fixes 2023-03-07 20:12:11 +01:00
Christian Zimmermann
e016059ad0 finish first version of cereal extension (more or less tested) 2023-02-28 17:50:56 +01:00
Christian Zimmermann
80ac604089 cxz cereal: more tests 2023-02-28 14:15:16 +01:00
Christian Zimmermann
36a22f51de add first parts of cereal extension 2023-02-27 20:09:06 +01:00
Christian Zimmermann
82fab9f7dc Merge branch 'dev' of git.f3l.de:chizeta/cnorxz into dev 2023-02-26 20:15:14 +01:00
Christian Zimmermann
a2b936c4da add basic_operations + first corresponding test 2023-02-26 20:15:05 +01:00
Christian Zimmermann
fee6d8e895 cmake lists: fix version string bug 2023-02-22 12:06:56 +01:00
Christian Zimmermann
039effb344 add config binary 2023-02-22 02:38:51 +01:00
Christian Zimmermann
229a913bcb move python stuff to separate repo 2023-02-21 19:31:53 +01:00
Christian Zimmermann
9a7daabd24 Merge branch 'dev' of git.f3l.de:chizeta/cnorxz into dev 2023-02-21 16:52:21 +01:00
Christian Zimmermann
b3d1ced728 switch to uuid as range id 2023-02-21 16:52:05 +01:00
Christian Zimmermann
3a7bd9c9e2 fix urange slice() + prange for and pfor expression 2023-01-30 01:13:14 +01:00
Christian Zimmermann
65e7539666 for: replace * by () in position calculation 2023-01-29 23:42:12 +01:00
Christian Zimmermann
792c3bd84e WIP: prange 2023-01-28 18:34:24 +01:00
Christian Zimmermann
f5f66461f7 merge 2023-01-28 02:13:14 +01:00
Christian Zimmermann
32ef2ef921 Merge branch 'dev' of git.f3l.de:chizeta/cnorxz into dev 2023-01-28 02:12:38 +01:00
Christian Zimmermann
62b77921f5 fixes + keep correct ordering in h5 table fields names 2023-01-28 02:05:50 +01:00
Christian Zimmermann
25b5c13608 h5_table: remove mCheckedFile 2023-01-26 19:55:29 +01:00
Christian Zimmermann
2547a450d8 hdf5: type declaration in separate file + some reorgs in table code 2023-01-25 18:31:03 +01:00
Christian Zimmermann
24ea3339f8 hdf5: group/table improvements 2023-01-25 00:30:12 +01:00
Christian Zimmermann
58fa19f514 hdf5: preliminary append (init) table test 2023-01-24 01:39:23 +01:00
Christian Zimmermann
6faaf7ea15 hdf5: include cc.h files + corresp compile fixes 2023-01-24 00:02:32 +01:00
Christian Zimmermann
0db94229bf WIP: more development on h5_table 2023-01-23 19:22:42 +01:00
Christian Zimmermann
59932895e9 add h5_types + class STabel : public Table ( field types known by compile time) 2023-01-22 23:34:30 +01:00
Christian Zimmermann
69a9344790 Merge branch 'restructure-rename' into dev 2023-01-22 15:42:06 +01:00
Christian Zimmermann
1f5843895e h5 table, untested 2023-01-22 15:41:42 +01:00
Christian Zimmermann
07428d1e6d fix install paths 2023-01-20 15:58:52 +01:00
Christian Zimmermann
66d5e5b741 index xpr + h5 table header file 2023-01-20 01:05:24 +01:00
Christian Zimmermann
02174f8371 hdf5: H5Oget_info: distinguish between versions 2023-01-18 19:12:41 +01:00
Christian Zimmermann
835b8e885f various fixes regarding extending ranges/arrays + hdf5 2023-01-18 18:57:17 +01:00
Christian Zimmermann
e6da712482 ranges: extend + array: init + extend + hdf5: adapt 2023-01-18 00:49:11 +01:00
Christian Zimmermann
d72bf23049 further hdf5 test 2023-01-15 03:18:21 +01:00
Christian Zimmermann
e331f6c4e2 first hdf5 test 2023-01-15 01:26:01 +01:00
Christian Zimmermann
b6455049c4 add hdf5 test build files 2023-01-13 15:42:15 +01:00
Christian Zimmermann
5dd114f03f add cmake files for hdf5 part + fix compile errors 2023-01-13 12:26:23 +01:00
Christian Zimmermann
caed6b4469 hdf5: group 2023-01-13 01:40:19 +01:00
Christian Zimmermann
631d187c91 begin hdf5 2023-01-12 19:29:45 +01:00
Christian Zimmermann
e8c8e519dc change operator* for index shared ptrs -> creates index packs instead of m/yindices 2023-01-11 19:02:34 +01:00
Christian Zimmermann
6bd7140ae3 fix pipeline... 2023-01-11 17:36:24 +01:00
Christian Zimmermann
55922490b2 change operator* for indices -> creates index packs instead of m/yindices 2023-01-11 17:32:52 +01:00
Christian Zimmermann
603d03971d replace std integral_constant by corresponding typedef CSizeT 2023-01-04 23:11:51 +01:00
Christian Zimmermann
b74ace2f43 update base/types.h 2023-01-04 23:06:02 +01:00
Christian Zimmermann
8469fa9fb2 yrange: replace index pack type 2023-01-04 11:27:18 +01:00
Christian Zimmermann
346f92f267 yrange: replace blockSizes by yformat 2023-01-04 11:15:51 +01:00
Christian Zimmermann
b1f9a38af7 mindex: replace type of ipack 2023-01-03 21:02:50 +01:00
Christian Zimmermann
8787ec7590 mindex: replace block sizes by format 2023-01-03 18:11:45 +01:00
Christian Zimmermann
53aa87c362 index format 2022-12-31 19:43:06 +01:00
Christian Zimmermann
0980934706 index pack 2022-12-31 15:18:26 +01:00
Christian Zimmermann
1ab0c21667 first array operation test 2022-12-30 13:32:27 +01:00
Christian Zimmermann
a4e32416ad array base: slice + op 2022-12-29 00:35:57 +01:00
Christian Zimmermann
b86ea957ba index format + slice 2022-12-28 21:21:11 +01:00
Christian Zimmermann
16f062b069 im com... 2022-12-21 22:06:17 +01:00
Christian Zimmermann
61cef892f3 ... 2022-12-21 00:06:21 +01:00
Christian Zimmermann
8209f14c71 include lindex 2022-12-20 21:53:59 +01:00
Christian Zimmermann
d25cbda2fc array_base: operator() and op function 2022-12-20 17:21:29 +01:00
Christian Zimmermann
07242a995e minor change 2022-12-20 00:52:23 +01:00
Christian Zimmermann
34c45e3dd9 fix compile errors 2022-12-20 00:07:59 +01:00
Christian Zimmermann
0fbd2d6f5b mrange: zip; todo: for all other index types 2022-12-14 01:48:17 +01:00
Christian Zimmermann
6963dd82cd index utils: index depth/dimension 2022-12-13 19:19:41 +01:00
Christian Zimmermann
79535c496f add get/set block sizes function for gmindex, yindex, xindex and dindex 2022-12-13 00:37:59 +01:00
Christian Zimmermann
f41ada859a im com 2022-12-12 02:15:42 +01:00
Christian Zimmermann
854e1a0533 slices 2022-12-06 19:34:42 +01:00
Christian Zimmermann
9938d43f9c rename darray_base -> carray_base, mdarray_base -> array_base, darray -> marray + rename corresponding files/tests 2022-12-06 14:48:44 +01:00
Christian Zimmermann
9aba24cf01 .gitlab-ci.yml: use my own centos image 2022-12-05 22:36:35 +01:00
Christian Zimmermann
9bfb5f4707 dynamic index multiplication 2022-12-05 00:14:00 +01:00
Christian Zimmermann
13467b800a fix cxz error macro (clang) 2022-12-04 21:57:18 +01:00
Christian Zimmermann
9ef055d9c9 revert ci 2022-12-04 19:21:28 +01:00
Christian Zimmermann
4d6a810704 try to fix pipeline 13 2022-12-04 19:13:21 +01:00
Christian Zimmermann
485dfe36c4 try to fix pipeline 12 2022-12-04 19:09:35 +01:00
Christian Zimmermann
4b6288beaf try to fix pipeline 11 2022-12-04 19:06:21 +01:00
Christian Zimmermann
addd19ca70 try to fix pipeline 10 2022-12-04 19:03:33 +01:00
Christian Zimmermann
0e84e2ffd8 try to fix pipeline 10 2022-12-04 19:03:04 +01:00
Christian Zimmermann
dcd2e4a87f try to fix pipeline 9 2022-12-04 18:59:52 +01:00
Christian Zimmermann
627fa9eb1a try to fix pipeline 8 2022-12-04 18:57:44 +01:00
Christian Zimmermann
5f85f13d66 try to fix pipeline 7 2022-12-04 18:55:49 +01:00
Christian Zimmermann
8025f657d6 try to fix pipeline 6 2022-12-04 18:55:00 +01:00
Christian Zimmermann
3866b603ce try to fix pipeline 5 2022-12-04 18:52:47 +01:00
Christian Zimmermann
a8fad26cfa try to fix pipeline 4 2022-12-04 18:44:35 +01:00
Christian Zimmermann
b1df3e1307 try to fix pipeline 3 2022-12-04 18:42:35 +01:00
Christian Zimmermann
9fad49a2eb try to fix pipeline 2 2022-12-04 17:49:17 +01:00
Christian Zimmermann
9c2b29ac07 try to fix pipeline 1 2022-12-04 17:42:37 +01:00
Christian Zimmermann
9210f59d39 more tests on index multiplication + corresponding fixes 2022-12-04 17:35:22 +01:00
Christian Zimmermann
38e011c979 first tests on index multiplication 2022-12-04 03:17:29 +01:00
Christian Zimmermann
b2fd81b764 add more range tests 2022-12-04 01:12:34 +01:00
Christian Zimmermann
1bd51ee700 shift index multiplication to separate file + extend to Sptr 2022-11-29 01:46:53 +01:00
Christian Zimmermann
a3a25af289 redefine index-index-multiplications 2022-11-27 23:51:15 +01:00
Christian Zimmermann
8513b6dcd3 2d opcont test 2022-11-27 04:28:46 +01:00
Christian Zimmermann
059093241b OpCont: again owns data (can have static size now); use (C)OpRoot for assignment-like operations 2022-11-27 03:38:10 +01:00
Christian Zimmermann
204b726acf minor fix 2022-11-27 01:25:59 +01:00
Christian Zimmermann
4f1ebb9986 1dim operation test + corresponding fixes 2022-11-27 00:27:34 +01:00
Christian Zimmermann
42a8acbc6e remove statics/ utils/ 2022-11-26 17:03:39 +01:00
Christian Zimmermann
3418ec9ee1 remove old test files 2022-11-26 16:28:00 +01:00
Christian Zimmermann
0e71d45a5b minor changes + mindex/yindex: further functionalities 2022-11-25 02:08:43 +01:00
Christian Zimmermann
25abf5e1b0 add src/opt/python/setup.py.in + update cmake project name + remove static cnorxz lib 2022-11-24 02:08:04 +01:00
Christian Zimmermann
7acc5c86ee remove old files 2022-11-23 23:26:27 +01:00
Christian Zimmermann
1f27826aff fixes/more functionalities in MIndex + add 2d Array test 2022-11-23 01:25:59 +01:00
Christian Zimmermann
216bb3f56e aindex: inherit yindex + yrange: specialize RangeCast + corrections in DArray classes + more DArray tests 2022-11-22 19:11:41 +01:00
Christian Zimmermann
a3d3d99c8d add first for tests 2022-11-22 00:58:50 +01:00
Christian Zimmermann
2f5f29f577 mrange: different members for blockSizes and lexBlockSizes 2022-11-20 23:18:58 +01:00
Christian Zimmermann
2745eee0ff src/tests/range_unit_test.cc: again fix signed vs unsigned comp 2022-11-18 19:53:43 +01:00
Christian Zimmermann
31bebecb23 further yrange tests 2022-11-18 19:50:19 +01:00
Christian Zimmermann
99eb72bb76 fix bug in DType + further yrange test 2022-11-17 19:00:58 +01:00
Christian Zimmermann
da4bf39c83 remove old files + first yr_test (to be extended) 2022-11-17 01:26:35 +01:00
Christian Zimmermann
3e54485b12 extend mr_test 2022-11-14 18:47:51 +01:00
Christian Zimmermann
3a6ffc209b change template args of RangeInterface (static polymorphism) + fixes in MRange -> first tests compile 2022-11-14 00:35:05 +01:00
Christian Zimmermann
62a9df39d3 add UR_Test + remove operator-> for index classes where it conflicts with c++ syntax 2022-11-13 02:23:33 +01:00
Christian Zimmermann
4e2244db79 finish mrange/mindex (unchecked) 2022-11-12 03:14:07 +01:00
Christian Zimmermann
113a0e7209 fix compile errors 2022-11-12 00:15:26 +01:00
Christian Zimmermann
fb94a382bb base/isq.h + base/iter.* + functional/fundamental.h + adaptions in mrange (WIP) 2022-11-08 22:36:16 +01:00
Christian Zimmermann
0197e7db6e more on MIndex + operator << for PosTypes 2022-11-06 22:58:46 +01:00
Christian Zimmermann
172110c5de start refactoring MIndex 2022-11-02 18:51:18 +01:00
Christian Zimmermann
6b2bbc3020 OpCont + adapt ifor memeber functions 2022-10-30 22:28:40 +01:00
Christian Zimmermann
c9f69ad25d extensions: finish basic arithmetic implementation for consecutive + avx 2022-10-30 12:12:53 +01:00
Christian Zimmermann
fbfd84f421 more on extensions... 2022-10-29 03:08:34 +02:00
Christian Zimmermann
cf7dcb816b WIP: avx 2022-10-25 23:45:05 +02:00
Christian Zimmermann
1befb14039 fixes + start extension code 2022-10-24 18:34:11 +02:00
Christian Zimmermann
e2405738c1 derive COpInterface : XprInterface; allow return values for Xpr (VXpr+DXpr -> templates) 2022-10-23 18:29:07 +02:00
Christian Zimmermann
fa1ea56d51 op_types: contraction (not finished) 2022-10-22 02:42:18 +02:00
Christian Zimmermann
e3fe04d5da DPos/DPosRef: -> static scalar; replace next() by sub() 2022-10-22 01:11:27 +02:00
Christian Zimmermann
f68c02565d im com (not finished) 2022-10-21 17:35:23 +02:00
Christian Zimmermann
483e3b4286 move xpr/op_xpr.* -> operation/op_xpr.* 2022-10-21 13:52:53 +02:00
Christian Zimmermann
4cb3977fb3 cxz_operation -> op_types 2022-10-21 13:40:12 +02:00
Christian Zimmermann
db623649ee move include/ranges/xpr -> include/xpr 2022-10-21 13:32:27 +02:00
Christian Zimmermann
98f71b874b more on operations 2022-10-21 02:24:30 +02:00
Christian Zimmermann
aafc6f0e2a xpr -> only one pos argument 2022-10-21 00:21:47 +02:00
Christian Zimmermann
477ea8d43d start operation refactoring 2022-10-20 02:58:24 +02:00
Christian Zimmermann
7904d77bd8 EPos + EFor (for extensions, simd vectorization, etc) 2022-10-18 00:30:05 +02:00
Christian Zimmermann
b47000d015 corrections in TFor 2022-10-17 12:20:09 +02:00
Christian Zimmermann
b0d002b7b1 re-enable index ifor 2022-10-16 23:05:48 +02:00
Christian Zimmermann
6fc3a50fa9 index_id 2022-10-16 18:37:14 +02:00
Christian Zimmermann
3eea7f2314 for.h 2022-10-16 00:55:14 +02:00
Christian Zimmermann
e2baceada7 xpr_base 2022-10-13 19:12:23 +02:00
Christian Zimmermann
85059f8024 xpr_unit_test: add more tests -> work 2022-10-13 15:58:17 +02:00
Christian Zimmermann
ade28d5122 rename directory xfor -> xpr 2022-10-13 14:50:15 +02:00
Christian Zimmermann
d555fabf40 remove most of static chains in vpos 2022-10-13 14:39:40 +02:00
Christian Zimmermann
d804f5db7e im com 2022-10-13 00:30:37 +02:00
Christian Zimmermann
c7e66f081c im com 2022-10-12 23:03:44 +02:00
Christian Zimmermann
73ded8c9a8 tests: fix signed vs unsigned again... 2022-10-12 16:53:26 +02:00
Christian Zimmermann
4dc6846845 first DPos test works 2022-10-12 15:28:35 +02:00
Christian Zimmermann
459ea690e5 more on DPos/VPos 2022-10-11 23:01:31 +02:00
Christian Zimmermann
ed6c90b95c new DPos/VPos + further macros 2022-10-11 18:36:23 +02:00
Christian Zimmermann
ee1fe52429 xfor_unit_test: signed vs unsigned 2022-10-10 17:01:37 +02:00
Christian Zimmermann
7e1cfa6b3a PosT: again linear 2022-10-09 16:59:12 +02:00
Christian Zimmermann
a142fdb466 im com 2022-10-06 18:32:56 +02:00
Christian Zimmermann
37dc3bf818 Pos_Test Multi works; change some things in near future 2022-09-28 23:28:07 +02:00
Christian Zimmermann
872d8f0d4a Pos_Test Basics works 2022-09-28 19:09:45 +02:00
Christian Zimmermann
321d6cd8fa more on pos type (not finished/checked/debugged) 2022-09-27 20:32:26 +02:00
Christian Zimmermann
cc52e86526 more on PosT 2022-09-20 23:52:54 +02:00
Christian Zimmermann
d497eb09ae change getStepSize: pass ptr id instead of index number 2022-09-18 22:50:07 +02:00
Christian Zimmermann
a880d1e0db start refactoring mrange + index interface offset (not finished) 2022-09-18 18:53:38 +02:00
Christian Zimmermann
59267fb040 src/tests/CMakeLists.txt: remove test sources (link against testlib instead) 2022-09-18 17:24:19 +02:00
Christian Zimmermann
47b2f3ee31 yrange.cc: fix undefined ref to ::range() 2022-09-18 17:06:51 +02:00
Christian Zimmermann
4c2945b683 range_unit_test: fix signed vs unsigned comparison 2022-09-18 17:04:25 +02:00
Christian Zimmermann
e542a37bf3 add dindex (-> standard index of RangeBase) 2022-09-18 16:19:27 +02:00
Christian Zimmermann
4212ed7ee9 crange.basic test works 2022-09-18 00:49:36 +02:00
Christian Zimmermann
a10770b4f1 container_index -> a/b index 2022-09-17 22:09:01 +02:00
Christian Zimmermann
5a71d00863 container_index -> a/b index 2022-09-17 22:08:01 +02:00
Christian Zimmermann
3044646b6a yrange implementations (part only) 2022-09-15 23:40:23 +02:00
Christian Zimmermann
3764f865e9 rename yindex.* -> yrange.* 2022-09-15 22:32:44 +02:00
Christian Zimmermann
9543342db4 further compile fixes 2022-09-15 16:45:45 +02:00
Christian Zimmermann
0dcf7d3b5a further renaming + fixes 2022-09-14 18:58:06 +02:00
Christian Zimmermann
0ec807c8fa fix some of the recently introduced compile errors 2022-09-13 00:31:12 +02:00
Christian Zimmermann
796bb50118 ext -> pos, expressions... 2022-09-12 16:48:45 +02:00
Christian Zimmermann
10db0908e0 im com 2022-09-12 01:09:51 +02:00
Christian Zimmermann
f6725f5356 rename range files 2022-09-11 17:23:59 +02:00
Christian Zimmermann
72e898606f im com 2022-09-11 17:20:09 +02:00
Christian Zimmermann
bc4ebf317b index_base.cc.h 2022-09-11 15:20:27 +02:00
Christian Zimmermann
3463e6ceea wip... 2022-09-11 02:48:30 +02:00
Christian Zimmermann
ebc0f5a807 wip: dynamic stuff; switched off most of the tests 2022-09-09 19:41:43 +02:00
Christian Zimmermann
5d473ddd8c wip... 2022-09-03 22:11:36 +02:00
Christian Zimmermann
05f4cb0abb wip: dynamic indices 2022-08-31 17:37:20 +02:00
Christian Zimmermann
3dd688bbed DArray (future Array) 2022-08-31 14:58:39 +02:00
269 changed files with 34818 additions and 19845 deletions

36
.github/workflows/main.yml vendored Normal file
View file

@ -0,0 +1,36 @@
# This file is based on https://github.com/satu0king/Github-Documentation-With-Doxygen/blob/master/main.yml
name: Doxygen Action
# Trigger workflow only on pushed to master branch:
on:
workflow_dispatch:
push:
branches: [ main ]
jobs:
build:
# The type of runner that the job will run on
runs-on: ubuntu-latest
# Steps represent a sequence of tasks that will be executed as part of the job
steps:
# Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
- uses: actions/checkout@v2
- name: Doxygen Action
uses: mattnotmitt/doxygen-action@v1.1.0
with:
# Path to Doxyfile
doxyfile-path: "./Doxyfile"
# Working directory
working-directory: "./doc/doxy"
- name: Deploy
uses: peaceiris/actions-gh-pages@v4
with:
github_token: ${{ secrets.GITHUB_TOKEN }}
publish_dir: ./doc/doxy/html
permissions:
contents: write

2
.gitignore vendored
View file

@ -5,3 +5,5 @@ install/
*/build/ */build/
*/install/ */install/
src/lib/hl_ops/*.cc src/lib/hl_ops/*.cc
doc/doxy/html/
doc/doxy/latex/

View file

@ -1,17 +0,0 @@
before_script:
- export GTEST_ROOT=/opt/gtest-1.8.0
image: docker.io/rqcd/centos-buildtools:7.2.1511
stages:
- build
build-centos:
stage: build
script:
- source /opt/rh/devtoolset-7/enable
- mkdir build
- cd build
- cmake3 ..
- make -j2
- make test

18
.woodpecker.yml Normal file
View file

@ -0,0 +1,18 @@
---
steps:
build:
image: chizeta/centos:8
commands:
- source /opt/rh/gcc-toolset-9/enable
- mkdir build-gcc
- cd build-gcc
- cmake3 -DSCALAR_BUILD=on ..
- make -j2
- make test
- cd ..
- mkdir build-clang
- cd build-clang
- CC=/usr/bin/clang CXX=/usr/bin/clang++ cmake3 -DRUN_PIPELINE=on -DSCALAR_BUILD=on ..
- make -j2
- make test

View file

@ -1,6 +1,38 @@
cmake_minimum_required(VERSION 2.8) cmake_minimum_required(VERSION 3.5)
project(multi_array) project(cnorxz)
# LIB VERSION
set(V_MAJOR 0)
set(V_MINOR 0)
set(V_PATCH 0)
set(VERSION "${V_MAJOR}.${V_MINOR}.${V_PATCH}")
# OPTIONS
option(SCALAR_BUILD "" OFF)
# INCLUDES
include(cmake/check_avx.cmake)
# GIT VARIABLES
execute_process(COMMAND bash "-c" "git rev-parse HEAD" OUTPUT_VARIABLE GIT_HASH OUTPUT_STRIP_TRAILING_WHITESPACE)
execute_process(COMMAND bash "-c" "git rev-parse --abbrev-ref HEAD" OUTPUT_VARIABLE GIT_BRANCH OUTPUT_STRIP_TRAILING_WHITESPACE)
# BUILD VERSION STRING
message(STATUS "git hash = ${GIT_HASH}")
message(STATUS "git branch = ${GIT_BRANCH}")
if(NOT ("${GIT_BRANCH}" EQUAL "release"))
string(SUBSTRING ${GIT_HASH} 0 7 GIT_HASH_SHORT)
set(VERSION "${VERSION}-${GIT_BRANCH}-${GIT_HASH_SHORT}")
endif()
message(STATUS "version = ${VERSION}")
# CHECK COMPILER
if(CMAKE_COMPILER_IS_GNUCXX) if(CMAKE_COMPILER_IS_GNUCXX)
if(NOT CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 7.0) if(NOT CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 7.0)
@ -10,20 +42,41 @@ else()
message(WARNING "compiler ${CMAKE_CXX_COMPILER_ID} officially not supported") message(WARNING "compiler ${CMAKE_CXX_COMPILER_ID} officially not supported")
endif() endif()
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Werror -std=c++17 -Wpedantic -Ofast -march=native -faligned-new -funroll-loops -fopenmp") # FLAGS
#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Werror -std=c++14 -g -Wpedantic -Ofast -march=native -faligned-new -funroll-loops -fopenmp -ftemplate-backtrace-limit=0")
#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Werror -std=c++14 -g -Wpedantic -O0 -march=native -faligned-new -funroll-loops -fopenmp") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Werror -std=c++17 -Wpedantic -O2 -march=native -faligned-new -funroll-loops -fopenmp")
# TESTING
enable_testing() enable_testing()
# INSTALL PATH
if(IS_ABSOLUTE "${CMAKE_INSTALL_PREFIX}") if(IS_ABSOLUTE "${CMAKE_INSTALL_PREFIX}")
set(INSTALL_PATH ${CMAKE_INSTALL_PREFIX}) set(INSTALL_PATH ${CMAKE_INSTALL_PREFIX})
else() else()
#set(INSTALL_PATH ${CMAKE_SOURCE_DIR}/install) #set(INSTALL_PATH ${CMAKE_SOURCE_DIR}/install)
get_filename_component(INSTALL_PATH ${CMAKE_BINARY_DIR}/${CMAKE_INSTALL_PREFIX} ABSOLUTE) get_filename_component(INSTALL_PATH ${CMAKE_BINARY_DIR}/${CMAKE_INSTALL_PREFIX} ABSOLUTE)
endif() endif()
message(WARNING "found absolute install path '${INSTALL_PATH}'") message(STATUS "found absolute install path '${INSTALL_PATH}'")
# SCALAR / INTRINSICS
if(NOT ${SCALAR_BUILD})
message(STATUS "check for intrinsics")
check_avx()
if(AVX_AVAIL)
message(STATUS "AVX available")
add_definitions("-DCXZ_HAVE_AVX")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -mavx")
else()
message(STATUS "AVX not available")
endif()
endif()
# CHECK LIBRARIES : GTest
message(STATUS "check for libraries")
find_package( GTest REQUIRED ) find_package( GTest REQUIRED )
if(GTest_FOUND) if(GTest_FOUND)
include_directories(${GTEST_INCLUDE_DIRS}) include_directories(${GTEST_INCLUDE_DIRS})
@ -31,6 +84,8 @@ else()
message(FATAL_ERROR "GTest not found") message(FATAL_ERROR "GTest not found")
endif() endif()
# CHECK LIBRARIES : Threads
find_package(Threads REQUIRED) find_package(Threads REQUIRED)
if(Threads_FOUND) if(Threads_FOUND)
#include_directories(${Threads_INCLUDE_DIRS}) #include_directories(${Threads_INCLUDE_DIRS})
@ -38,4 +93,42 @@ else()
message(FATAL_ERROR "Threads not found") message(FATAL_ERROR "Threads not found")
endif() endif()
# CHECK LIBRARIES : hdf5
if(DEFINED ENABLE_hdf5)
set(ENABLE_hdf5 ${ENABLE_hdf5} CACHE BOOL "enable hdf5")
else()
set(ENABLE_hdf5 TRUE CACHE BOOL "enable hdf5")
endif()
# CHECK LIBRARIES : cereal
if(DEFINED ENABLE_cereal)
set(ENABLE_cereal ${ENABLE_cereal} CACHE BOOL "enable hdf5")
else()
set(ENABLE_cereal TRUE CACHE BOOL "enable hdf5")
endif()
find_package(cereal QUIET)
if(cereal_FOUND)
message(STATUS "found cereal")
if(ENABLE_cereal)
message(STATUS "enable cereal")
add_definitions(-DHAVE_CEREAL)
endif()
else()
message(STATUS "no cereal")
if(ENABLE_cereal)
message(FATAL_ERROR "cereal has been enabled but the cereal library has not been found")
endif()
endif()
# DEFINES
add_definitions(-DVERSION="${VERSION}")
add_definitions(-DGIT_COMMIT="${GIT_HASH}")
add_definitions(-DCXX_FLAGS="${CMAKE_CXX_FLAGS}")
# CONTINUE WITH SUB-DIRECTORIES
add_subdirectory(src) add_subdirectory(src)

21
LICENSE Normal file
View file

@ -0,0 +1,21 @@
MIT License
Copyright (c) 2024 Christian Zimmermann
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

198
README.md
View file

@ -1,120 +1,154 @@
# Container with Native Operation Routines by XZ (CNORXZ) # Container with Native Operation Routines and Expressions (CNORXZ)
(as always, the name was there before the acronym)
![Image](./cnorxz_logo.png)
## Description ## Description
This library provides a framework for handling multi dimensional containers. This includes the basic container class template `ArrayBase` and their derivates, the Range class templates on which the containers are defined, as well as some operation class templates, which allow comfortable calling of operations on the containers. This library provides a framework for handling multi dimensional data containers (arrays or array-like types), their meta data, and several kinds of operations on one or more of them.
## Build instructions ## Build instructions
The library can be installed by the following procedure (`gtest` required): The library can be installed by the following procedure (`gtest` required):
```bash ```bash
git clone git@git.f3l.de:chizeta/cnorxz.git <SOURCE_DIR> git clone git@git.f3l.de:chizeta/cnorxz.git <LIBRARY_ROOT_DIR>
mkdir <BUILD_DIR>
cd <BUILD_DIR> cd <BUILD_DIR>
cmake -DCMAKE_INSTALL_PREFIX:PATH=<INSTALL_DIR> <SOURCE_DIR> cmake -DCMAKE_INSTALL_PREFIX:PATH=<INSTALL_DIR> <LIBRARY_ROOT_DIR>
make install make install
``` ```
## Usage and Examples To build the doxygen:
```bash
cd <SOURCE_DIR>/doc/doxy
doxygen Doxyfile
```
## Linking
To use the features of the libraries one has to include `cnorxz.h` and link against the `libcnorxz.so`. To use the features of the libraries one has to include `cnorxz.h` and link against the `libcnorxz.so`.
The tools of the library are accessible within the namespace `CONORXZ`. The tools of the library are accessible within the namespace `CNORXZ`.
### Some Terms ## Documentation
* Ranges: A set of meta data which is mapped onto the linear position. Every container is supposed to be defined on at least one Range. In the simplest case a Range space "containes" the numbers [0,...,rangesize]. Ranges have to be created via the corresponding factory and only exist within a shared pointer. They cannot be copied. The reason is, that every operation performed on the containers, has to identify common sets of ranges, on which the containers are defined. Every range inherits the `RangeBase` class. (Also consider doxygen)
* Indices: They can be thought of as iterators of the range space. In the special case of the `ContainerIndex` it is also an iterator over the corresponding container. The index type must be known at compile time (static polymorphism). Indices on a range can be obtained by `getIndex( range )`. For Container Indices call the `begin()` function of a `Array`. Indices are crucial for defining operations. ### Basics and Library organization
* `Array<T,Ranges...>`: Contains data of type `T` and is defined on `Ranges...`. This library consists of several building blocks. For simple usage, the most important building blocks are [ranges](#sec-ranges), [indices](#sec-indices) and [arrays](#sec-array-types).
* `[Const]Slice<T,Ranges...>`: Views data of type `T` and acts as an Array defined on `Ranges...`.
* `FunctionalArray`: Additional template argument indicating the funtion. The value at some position is then defined by the function value obtained from the meta data of the indices/ranges.
On each of these types one can perform an operation by calling `operator(...)` where within the braces the corresponding indices have to be specified (see example below). #### Ranges {#sec-ranges}
### Example Basically, a *range* defines a meta data space. There are several range class types, which are derived from the abstract base class `RangeBase`. Ranges can only be created by the corresponding factory and exclusively exist within a shared pointer; they cannot be copied. Available range class types are:
```c++ * `CRange` : Classic one-dimensional range. The meta data space is simply given by integer numbers running from `0` to `size-1`. The range size is determined at runtime.
#include "cnorxz.h" * `URange<MetaT>` : Generic One-dimensional range. The meta data space is user defined, the meta data type is passed as template argument. The range size is determined at runtime.
namespace cnx = CNORXZ; * `SRange<MetaT,S>` : The same as `URange`, but the range length is fixed at compile time by the template integer variable `S`.
typedef cnx::SingleRange<double,cnx::SpaceType::ANY> DRange; * `PRange<RangeT>` : Partial or sub-range, i.e. a user-defined subspace of another range. The type of the range must be known at compile time, the subspace can be specified at runtime.
typedef cnx::SingleRangeFactory<double,cnx::SpaceType::ANY> DRangeF;
typedef cnx::SingleRange<std::string,cnx::SpaceType::ANY> SRange;
typedef cnx::SingleRangeFactory<std::string,cnx::SpaceType::ANY> SRangeF;
typedef cnx::SingleRange<size_t,cnx::SpaceType::NONE> CRange; // also provided as 'ClassicR'
typedef cnx::SingleRangeFactory<size_t,cnx::SpaceType::NONE> CRangeF;
/*create ranges*/ * `MRange<RangeTs...>` : Multi-dimensional range, spanned by a set of ranges. The number of ranges, as well as their types must be known at compile time.
std::vector<double> meta1({...});
std::vector<double> meta2({...});
std::vector<std::string> meta3({...});
DRangeF drf1(meta1); * `YRange` : The same as `MRange` but the number of ranges and their types can be specified at runtime.
DRangeF drf2(meta2);
SRangeF srf(meta3);
CRangeF crf(10); // specialized in this case; only size needed.
auto dr1 = cnx::createExplicit( drf1 ); #### Indices {#sec-indices}
auto dr2 = cnx::createExplicit( drf2 );
auto sr = cnx::createExplicit( srf );
auto cr = cnx::createExplicit( crf );
cnx::Array<double,DRange,DRange,SRange,CRange> ma_a(dr1,dr2,sr,cr,0); For each range type there is a corresponding index type (`CIndex`, `UIndex<MetaT>`, `SIndex<MetaT,S>`, `PIndex<IndexT>`, `MIndex<IndexTs...>`, `YIndex`). They act as const iterators on the ranges and are a crucial component to define operations on containers. In contrast to the ranges, all index types must be known at compile time (static polymorphism, `IndexInterface<Index,MetaT>`).
cnx::Array<double,SRange,SRange> ma_b(sr,sr,0);
/* assign some values... */ Apart from range specific indices, there exist also special indices:
double val = 1.;
for(auto& x: ma_a){ * `DIndex` : Dynamic index wrapper, for the case that the index type cannot be determined at compile time.
x = val += 1;
* `AIndex<T>` : Array index. Const iterators pointing to the data of an array-type object with data type `T`.
* `BIndex<T>` : The same as `AIndex`, but not const.
#### Array types {#sec-array-types}
Arrays or array-like types contain or view datasets and are derived from `CArrayBase<T>` (const) or `ArrayBase<T>` for a given data type `T`. All array types are defined on a range, their data can be accessed or iterated over using suitable indices. The array-type actually containing data is called `MArray<T>`. Moreover, there exist array-types that do not contain data, but view the data of other arrays or at least parts of the data. These are called `CSlice<T>` (const view) or `Slice`.
#### Expressions and Operations
In the context of this library, *expressions* are classes representing an expression that is supposed to be executed at given points during an iteration proceedure that involves one or more indexed quantities. Each expression type must fulfill the following requirements:
* There must be an implementation of `operator()` taking a multi-position argument indicating the position for the current iteration of each involved object according to its indices. The function can have an expression defined return value, which can be further processed.
* There must be an implementation of `rootSteps()` taking an index ID as argument. The function should return jump sizes for each involved object corresponding to the given index.
Each expression `Xpr` should be derived from the class `XprInterface<Xpr>`, where `Xpr` is a recurring template argument (static polymorphism).
There are two important expression types:
* *For* expressions: They represent a for loop over a given index.
* *Operations*: They correspond to one or more indexed array types and given operation on or between them. If an operation handles nothing but the access to one single array, it is called *Operation* *Root*.
Example:
```cpp
#include "cnroxz.h"
using namespace CNORZX;
RangePtr r = CRangeFactory(3).create(); // [0,1,2]
RangePtr s = CRangeFactory(5).create(); // [0,1,2,3,4]
RangePtr t = URangeFactory<Int>(Vector<Int>{4,5,6}).create(); // [4,5,6]
i = std::make_shared<CIndex>(r);
j = std::make_shared<CIndex>(s);
k = std::make_shared<UIndex<Int>>(t);
MArray<Double> a(r*s*t); // 3-dim array, dimensions = [3,5,3], size = 45
MArray<Double> b(r*t); // 2-dim array, dimensions = [3,3], size = 9
MArray<Double> c(s*t); // 2-dim array, dimensions = [3,5], size = 15
// set array element values of a,b,c here...
c(j*k) += ( a(i*j*k) * b(j*k) * xpr(k) ).c(i);
/* Explanation of the above line:
c(j*k), a(i*j*k), b(j*k) and xpr(k) are operation roots, i.e.
they manage access to the arrays c,a,b and the meta data space of index k
The operations between the operation roots are also operations in the
sense of this nomenclature, i.e. a(i*j*k) * b(j*k) is again an operation.
The operation member function c() creates contraction, i.e. a for loop
over the given index (i). If no further functions are specified, the values
returned by the underlying operations are summed up for equivalent index
combinations.
The += invokes a for loop over the indices on the l.h.s.. The values returned
by the expression on the r.h.s. are added to the l.h.s. Something similar could be done
with a = operator. Then the values would just be assigned instead of added.
*/
// Equivalent C-stype for loop (if a,b,c were C-style arrays):
for(size_t j = 0; j < s; ++j){
for(size_t k = 0; k < t; ++k){
int kv = k+4;
double x = 0;
// the contraction part:
for(size_t i = 0; i < r; ++i){
x += a[i*s*t+j*t+k] * b[j*t+k] * kv;
}
c[j*t+k] += x;
}
} }
for(auto& x: ma_b){
x = val /= 2.;
}
cnx::FunctionalArray<double,plus<double>,DRange,DRange> fma(dr1,dr2);
cnx::Array<double,DRange,DRange> res1(dr1,dr2);
cnx::Array<double,DRange,DRange> res2(dr1,dr2);
/* get indices... */
auto i1 = cnx::getIndex( dr1 );
auto i2 = cnx::getIndex( dr2 );
auto i3 = cnx::getIndex( sr );
auto i4 = cnx::getIndex( sr );
auto i5 = cnx::getIndex( cr );
i3->at(<metaString>);
i5->at(<metaNum>);
/* performs plus operation on each element in hypercube spanned by i1,i2,i4
* and sums up resulting values by iterating over i4. i3 and i5 are fixed to the positions
* given by the meta data above : */
res1(i1,i2) += (ma_a(i1,i2,i4,i5) + ma_b(i4,i3)).c(i4);
/* calculates i2.meta() + i1.meta() and divide res1 at the corresponding entry by the result */
res2(i1,i2) = res1(i1,i2) / fma(i2,i1)
``` ```
Further examples will follow; you can also look in the test executable source files in `./src/test/*.cc` More documentation will follow...
# Multithreading ## Acknowledgments
Multithreading can be enabled by the operation class member function `par()`, which will parallelize the top loop. E.g. for the operation in the example above: GitHub Doxygen Task based on work by [satu0king](https://github.com/satu0king/Github-Documentation-With-Doxygen/tree/master).
```c++
/* Enable multithreading for the loop over i1 */
res1(i1,i2).par() = (ma_a(i1,i2,i4,i5) + ma_b(i4,i3)).c(i4);
```
Caution: If you want to multithread operations over functional arrays, you have to make sure by yourself that involved functors are either static or const (const member variables).
# Planned features I want to thank Gesina Schwalbe for creating the logo.
Basically the structure of the operation routines allows in some cases (at least in those, where it is possible for simple c++ for loops) vectorization. So far the necessary implamentations are not done, but it is planned to enable these features.
# Known Issues
I didn't care that much about error handling because of missing time. There it might happen that you declare a `Array` or `Slice` and an operation on it yields a segfault because it was forgotten to instancate the underlying container. Of course, there should be some mechanism, that catches such things, but due to the afore mentioned lack of time, it has not been implemented in every case. If you encounter such problems, pleas tell me, but be aware, that I won't fix it very soon.
There are unit tests, which cover the all crucial parts of this library, but probably not every special case. Hence, there is no warranty, that, if you do something fancy I didn't consider, everything works fine.

14
TODO Normal file
View file

@ -0,0 +1,14 @@
include/operation/op_types.cc.h@225: "build and execute assign expression forwarding outer index"
include/operation/op_types.cc.h@498: "implement ifor with func arg"
opt/hdf5/include/h5_content_base.h@23: "IO save error handling"
opt/hdf5/lib/h5_dataset.cc@124: "all sub-ranges explicity"
lib/ranges/crange.cc@94: "preliminary solution (TODO: implement xpr that simply returns PosT value)"
include/ranges/srange.cc.h@307: "check for selected static sizes of SRange -> return SRange"
include/xpr/for.cc.h@324: "check for write access"
include/base/dtype.cc.h@23: "for tuple use vector<DType>"
include/ranges/urange.cc.h@384: "else general transform using DType (better than nothing), to be implemented"
include/ranges/urange.cc.h@448: "else general transform using DType (better than nothing), to be implemented"
include/array/array_base.cc.h@184: "check further compatibility of index/range format"
include/array/array_base.cc.h@376: "check further compatibility of index/range format"
include/ranges/index_base.cc.h@109: "if this assert never applies, remove mPtrId (-> Defaults)"

24
cmake/check_avx.cmake Normal file
View file

@ -0,0 +1,24 @@
macro(check_avx)
include(CheckCXXSourceCompiles)
set(CMAKE_REQUIRED_FLAGS "-Wall -Werror -Wpedantic -std=c++17 -mavx")
check_cxx_source_compiles("
#include <immintrin.h>
#include <iostream>
int main()
{
const double a[4] = { 0,0,0,0 };
const double b[4] = { 0,0,0,0 };
double o[4] = { 0,0,0,0 };
__m256d av = _mm256_load_pd(a);
__m256d bv = _mm256_load_pd(b);
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(o, ov);
std::cout << o[0] << std::endl;
return 0;
}
"
AVX_AVAIL
)
endmacro()

BIN
cnorxz_logo.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

2774
doc/doxy/Doxyfile Normal file

File diff suppressed because it is too large Load diff

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.4 KiB

36
doc/doxy/header.html Normal file
View file

@ -0,0 +1,36 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "https://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en-US">
<head>
<meta http-equiv="Content-Type" content="text/xhtml;charset=UTF-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=11"/>
<meta name="generator" content="Doxygen 1.10.0"/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<title>CNORXZ: Container with Native Operation Routines and Expressions (CNORXZ)</title>
<link href="tabs.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="dynsections.js"></script>
<script type="text/javascript" src="clipboard.js"></script>
<script type="text/javascript" src="cookie.js"></script>
<link href="search/search.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="search/searchdata.js"></script>
<script type="text/javascript" src="search/search.js"></script>
<link href="doxygen.css" rel="stylesheet" type="text/css" />
</head>
<link rel="icon" href="$relpath^cnorxz_logo_mini.png" type="image/x-icon" />
<body>
<div id="top"><!-- do not remove this div, it is closed by doxygen! -->
<div id="titlearea">
<table cellspacing="0" cellpadding="0">
<tbody>
<tr id="projectrow">
<td id="projectlogo"><img alt="Logo" src="cnorxz_logo_mini.png"/></td>
<td id="projectalign">
<div id="projectname">CNORXZ
</div>
<div id="projectbrief">Container with Native Operation Routines and Expressions</div>
</td>
</tr>
</tbody>
</table>
</div>
<!-- end header part -->

View file

@ -0,0 +1 @@
../../../cnorxz_logo.png

View file

@ -2,5 +2,14 @@
include_directories(${CMAKE_SOURCE_DIR}/src/include) include_directories(${CMAKE_SOURCE_DIR}/src/include)
add_subdirectory(tests) add_subdirectory(tests)
add_subdirectory(lib) add_subdirectory(lib)
add_subdirectory(bin)
install(DIRECTORY include/ DESTINATION ${INSTALL_PATH}/include) if(ENABLE_hdf5)
add_subdirectory(opt/hdf5)
endif()
if(ENABLE_cereal)
add_subdirectory(opt/cereal)
endif()
install(DIRECTORY include/ DESTINATION ${INSTALL_PATH}/include/cnorxz)

6
src/bin/CMakeLists.txt Normal file
View file

@ -0,0 +1,6 @@
add_executable(cnorxz-config config.cc)
add_dependencies(cnorxz-config cnorxz)
target_link_libraries(cnorxz-config cnorxz)
install(TARGETS cnorxz-config RUNTIME DESTINATION ${INSTALL_PATH}/bin)

62
src/bin/config.cc Normal file
View file

@ -0,0 +1,62 @@
// -*- C++ -*-
/**
@file bin/config.cc
@brief Program for printing cnorxz configurations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include <cstdlib>
#include <iostream>
#include <map>
#include <functional>
#include "base/config.h"
using CNORXZ::String;
using CNORXZ::SizeT;
typedef std::map<String,std::function<String(void)>> CMapT;
auto configMap()
{
CMapT m;
m["--version"] = CNORXZ::Config::version;
m["--commit"] = CNORXZ::Config::commit;
m["--flags"] = CNORXZ::Config::flags;
return m;
}
void printUsage(const String& prog, const CMapT& cm)
{
std::cout << "usage: " << prog << " ";
for(const auto& x: cm){
std::cout << "[" << x.first << "] ";
}
std::cout << std::endl;
}
int main(int argc, char** argv)
{
const String prog(argv[0]);
const auto cm = configMap();
if(argc == 1){
printUsage(prog, cm);
}
try {
for(SizeT i = 1; i != static_cast<SizeT>(argc); ++i){
std::cout << cm.at( String(argv[i]) )() << std::endl;
}
}
catch(const std::out_of_range& e){
std::cerr << "caught exception: " << e.what() << std::endl;
printUsage(prog, cm);
return 1;
}
catch(...){
std::cerr << "caught generic exception" << std::endl;
}
return 0;
}

View file

@ -1,41 +0,0 @@
#include "access.h"
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
/************************
* AccessTemplate *
************************/
template <class AccessClass>
auto AccessTemplate<AccessClass>::get(size_t pos)
{
return THIS().get(pos);
}
template <class AccessClass>
auto AccessTemplate<AccessClass>::get(size_t pos) const
{
return THIS().get(pos);
}
template <class AccessClass>
auto AccessTemplate<AccessClass>::oget(size_t pos) const
{
return THIS().oget(pos);
}
template <class AccessClass>
template <class F, typename Op, class ExtType>
void AccessTemplate<AccessClass>::exec(size_t pos, const Op& op, ExtType e) const
{
return THIS().template exec<F>(pos,op,e);
}
} // namespace CNORXZ

View file

@ -1,173 +0,0 @@
#ifndef __cxz_access_h__
#define __cxz_access_h__
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
template <class T>
struct VType
{
typedef T type;
static constexpr size_t MULT = sizeof(type)/sizeof(T);
};
template <>
struct VType<double>
{
typedef v256 type;
static constexpr size_t MULT = sizeof(type)/sizeof(double);
};
template <template <typename...> class F,typename... Ts>
inline auto mkVFuncPtr(const std::shared_ptr<F<Ts...>>& f)
{
return std::shared_ptr<F<typename VType<Ts>::type...>>();
// empty, implement corresponding constructors...!!!
}
template <template <typename...> class F,typename... Ts>
inline auto mkVFunc(const F<Ts...>& f)
{
return F<typename VType<Ts>::type...>();
// empty, implement corresponding constructors...!!!
}
template <class F>
using VFunc = decltype(mkVFunc(std::declval<F>()));
//template <class F>
//using VFunc = F;
template <typename T, class F, class... Indices>
class OpAccess
{
private:
std::tuple<std::shared_ptr<Indices>...> mInds;
public:
static constexpr bool ISSTATIC = false;
template <typename Op, class ExtType>
inline void operator()(T*& t, size_t pos, const Op& op, ExtType e)
{
F::selfApply(t[pos](mInds), op.get(e)); // s.th. like that
// TODO for classes related to the r.h.s.:
// forward get(e) to elements returned by get(e) until basic types are reached
// (also same for rootSteps etc...) !!!!
// introduce traits !!!!
// !!!!
}
};
// static polymorphism
template <class AccessClass>
class AccessTemplate
{
public:
typedef AccessClass AC;
AccessTemplate(const AccessTemplate& in) = default;
AccessTemplate(AccessTemplate&& in) = default;
AccessTemplate& operator=(const AccessTemplate& in) = default;
AccessTemplate& operator=(AccessTemplate&& in) = default;
AccessClass& THIS() { return static_cast<AccessClass&>(*this); }
const AccessClass& THIS() const { return static_cast<const AccessClass&>(*this); }
inline auto get(size_t pos);
inline auto get(size_t pos) const;
inline auto oget(size_t pos) const;
template <class F, typename Op, class ExtType>
inline void exec(size_t pos, const Op& op, ExtType e) const;
protected:
AccessTemplate() = default;
};
template <typename T>
class PointerAccess : public AccessTemplate<PointerAccess<T>>
{
public:
typedef T value_type;
typedef T in_type;
static constexpr size_t VSIZE = sizeof(value_type) / sizeof(in_type);
friend class AccessTemplate<PointerAccess<T>>;
private:
PointerAccess() = default;
T* mPtr = nullptr;
T* mOrigPtr = nullptr;
public:
PointerAccess(T* ptr, T* origPtr) : mPtr(ptr), mOrigPtr(origPtr) {}
PointerAccess(const PointerAccess& in) = default;
PointerAccess(PointerAccess&& in) = default;
PointerAccess& operator=(const PointerAccess& in) = default;
PointerAccess& operator=(PointerAccess&& in) = default;
T* get(size_t pos) { return mPtr+pos; }
T* get(size_t pos) const { return mPtr+pos; }
PointerAccess<T>& set(size_t pos) { mPtr = mOrigPtr + pos; return *this; }
T* oget(size_t pos) const { return mOrigPtr+pos; }
template <class F, typename Op, class ExtType>
inline void exec(size_t pos, const Op& op, ExtType e) const
{
F::selfApply(*get(pos),op.get(e));
}
};
template <typename T>
class VPointerAccess : public AccessTemplate<VPointerAccess<T>>
{
public:
typedef typename VType<T>::type value_type;
typedef T in_type;
static constexpr size_t VSIZE = sizeof(value_type) / sizeof(in_type);
friend class AccessTemplate<VPointerAccess<T>>;
private:
VPointerAccess() = default;
T* mPtr = nullptr;
T* mOrigPtr = nullptr;
public:
VPointerAccess(T* ptr, T* origPtr) : mPtr(ptr), mOrigPtr(origPtr) {}
VPointerAccess(const PointerAccess<T>& in) : mPtr(in.get(0)), mOrigPtr(in.oget(0)) {}
VPointerAccess(const VPointerAccess& in) = default;
VPointerAccess(VPointerAccess&& in) = default;
VPointerAccess& operator=(const VPointerAccess& in) = default;
VPointerAccess& operator=(VPointerAccess&& in) = default;
value_type* get(size_t pos) { return reinterpret_cast<value_type*>(mPtr+pos); }
value_type* get(size_t pos) const { return reinterpret_cast<value_type*>(mPtr+pos); }
VPointerAccess<T>& set(size_t pos) { mPtr = mOrigPtr + pos; return *this; }
value_type* oget(size_t pos) const { return reinterpret_cast<value_type*>(mOrigPtr+pos); }
template <class F, typename Op, class ExtType>
inline void exec(size_t pos, const Op& op, ExtType e) const
{
F::selfApply(*get(pos),op.template vget<value_type>(e));
}
};
} // namespace CNORXZ
#endif

View file

@ -1,89 +0,0 @@
#ifndef __cxz_allocator__
#define __cxz_allocator__
#include <cstdlib>
#include <new>
#include <vector>
#include <cstdint>
#include <cassert>
#include <iostream>
#define MIB_SIZE 1024*1024 // 1MiB
#define WARN_SIZE MIB_SIZE*100 // 100 MiB
namespace CNORXZInternal
{
template <typename T>
struct Allocator
{
typedef T value_type;
static constexpr size_t type_size = sizeof(value_type);
static constexpr size_t N = 32;
struct VX
{
alignas(N) char x[N];
};
Allocator() = default;
template <typename U>
Allocator(const Allocator<U>& x) {}
T* allocate(size_t n)
{
const size_t nn = n*type_size;
if(nn >= WARN_SIZE){
std::cout << __func__ << ": WARNING: allocating " << nn/(MIB_SIZE) << " MiB" << std::endl;
}
const size_t off = nn%N;
const size_t nnx = (off == 0) ? nn : nn + N - off;
const size_t nnd = nnx/N;
VX* vx = new VX[nnd];
return reinterpret_cast<T*>(vx);
}
void deallocate(T* p, size_t n)
{
VX* vx = reinterpret_cast<VX*>(p);
delete [] vx;
}
};
template <class T, class U>
bool operator==(const Allocator<T>& a, const Allocator<U>& b)
{
return true;
}
template <class T, class U>
bool operator!=(const Allocator<T>& a, const Allocator<U>& b)
{
return false;
}
} // namespace CNORXZInternal
namespace CNORXZ
{
template <typename T>
using vector = std::vector<T,CNORXZInternal::Allocator<T>>;
template <typename T>
inline std::vector<T> toStdVec(const vector<T>& v)
{
return std::vector<T>(v.begin(), v.end());
}
template <typename T>
inline vector<T> toMatVec(const std::vector<T>& v)
{
return vector<T>(v.begin(), v.end());
}
} // namespace CNORXZ
#endif

View file

@ -1,35 +0,0 @@
#include "arith.h"
namespace CNORXZ
{
template <class F>
template <class... Ops>
auto StaticFunctionBase<F>::mk(const Ops&... ops)
{
return Operation<typename F::value_type,F,Ops...>(ops...);
}
template <class F>
template <size_t N, class Tuple, typename... As>
inline auto StaticFunctionBase<F>::xapply(const Tuple& tp, As... as)
{
if constexpr(N > 0){
return xapply<N-1>(tp, std::get<N>(tp), as...);
}
else {
return F::apply(std::get<0>(tp), as...);
}
}
template <class F>
template <typename... As>
inline auto StaticFunctionBase<F>::apply(const std::tuple<As...>& arg)
{
return xapply<sizeof...(As)-1>(arg);
//return ArgPack<sizeof...(As)-1>::template mk<F,std::tuple<As...> >(arg);
}
}

View file

@ -1,213 +0,0 @@
#ifndef __cxz_arith_h__
#define __cxz_arith_h__
#include <functional>
namespace CNORXZ
{
//template <typename T, class F, typename... As>
template <class F>
struct StaticFunctionBase
{
static constexpr bool FISSTATIC = true;
typedef F function;
//typedef typename F::value_type value_type;
template <class... Ops>
static auto mk(const Ops&... ops);
template <size_t N, class Tuple, typename... As>
static inline auto xapply(const Tuple& tp, As... as);
template <typename... As>
static inline auto apply(const std::tuple<As...>& arg);
};
// OPERATIONS (STATIC)
template <typename T>
struct identity : public StaticFunctionBase<identity<T>>
{
//static constexpr bool FISSTATIC = true;
using StaticFunctionBase<identity<T>>::apply;
typedef T value_type;
static inline T apply(T a)
{
return a;
}
static inline T selfApply(T& a1, const T& a2)
{
return a1 = a2;
}
};
template <typename T, typename U>
using plusv = decltype(std::declval<T>()+std::declval<U>());
template <typename T, typename U>
using minusv = decltype(std::declval<T>()-std::declval<U>());
template <typename T, typename U>
using multipliesv = decltype(std::declval<T>()*std::declval<U>());
template <typename T, typename U>
using dividesv = decltype(std::declval<T>()/std::declval<U>());
template <typename T, typename U>
struct plusx : public StaticFunctionBase<plusx<T,U>>
{
static constexpr bool FISSTATIC = true;
using StaticFunctionBase<plusx<T,U>>::apply;
typedef plusv<T,U> value_type;
static inline value_type apply(T a1, U a2)
{
return a1 + a2;
}
static inline T& selfApply(T& a1, const T& a2)
{
return a1 += a2;
}
};
template <typename T, typename U>
struct minusx : public StaticFunctionBase<minusx<T,U>>
{
static constexpr bool FISSTATIC = true;
using StaticFunctionBase<minusx<T,U>>::apply;
typedef minusv<T,U> value_type;
static inline value_type apply(T a1, U a2)
{
return a1 - a2;
}
};
template <typename T, typename U>
struct multipliesx : public StaticFunctionBase<multipliesx<T,U>>
{
static constexpr bool FISSTATIC = true;
using StaticFunctionBase<multipliesx<T,U>>::apply;
typedef multipliesv<T,U> value_type;
static inline value_type apply(T a1, U a2)
{
return a1 * a2;
}
};
template <typename T, typename U>
struct dividesx : public StaticFunctionBase<dividesx<T,U>>
{
static constexpr bool FISSTATIC = true;
using StaticFunctionBase<dividesx<T,U>>::apply;
typedef dividesv<T,U> value_type;
static inline value_type apply(T a1, U a2)
{
return a1 / a2;
}
};
template <typename T>
struct negate : public StaticFunctionBase<negate<T>>
{
static constexpr bool FISSTATIC = true;
using StaticFunctionBase<negate<T>>::apply;
typedef T value_type;
static inline T apply(T a)
{
return -a;
}
};
template <typename T>
using plus = plusx<T,T>;
template <typename T>
using minus = minusx<T,T>;
template <typename T>
using multiplies = multipliesx<T,T>;
template <typename T>
using divides = dividesx<T,T>;
// OPERATIONS (STATIC)
template <typename R, typename... Args>
class function
{
public:
static constexpr bool FISSTATIC = false;
private:
std::function<R(Args...)> mF;
public:
function() = default;
function(const std::function<R(Args...)>& in) : mF(in) {}
inline R operator()(const Args&... args)
{
return mF(args...);
}
template <size_t N, class Tuple, typename... As>
static inline auto xapply(const std::function<R(Args...)>& ff, const Tuple& tp, As... as)
{
if constexpr(N > 0){
return xapply<N-1>(ff, tp, std::get<N>(tp), as...);
}
else {
return ff(std::get<0>(tp), as...);
}
}
inline R operator()(const std::tuple<Args...>& args)
{
return xapply<sizeof...(Args)-1>(mF, args);
}
};
#include <cmath>
#define regFunc1(fff) template <typename T>\
struct x_##fff : public StaticFunctionBase<x_##fff<T>> {\
static constexpr bool FISSTATIC = true;\
typedef T value_type; \
static inline T apply(T a){\
return fff(a); } };
#include "extensions/math.h"
#undef regFunc1
template <size_t N>
struct x_ipow
{
static constexpr bool FISSTATIC = true;
template <typename T>
static inline T apply(T a)
{
if constexpr(N > 0){
return a * x_ipow<N-1>::apply(a);
}
else {
return a;
}
}
};
} // end namespace CNORXZInternal
#include "arith.cc.h"
#endif

View file

@ -0,0 +1,109 @@
// -*- C++ -*-
/**
@file include/array/aindex.cc.h
@brief Array index template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_aindex_cc_h__
#define __cxz_aindex_cc_h__
#include "aindex.h"
namespace CNORXZ
{
template <typename T>
AIndex<T>::AIndex(const T* data, const RangePtr& range, SizeT lexpos) :
YIndex(range, lexpos),
mCData(data)
{}
template <typename T>
AIndex<T>::AIndex(const T* data, const YIndex& yindex) :
YIndex(yindex),
mCData(data)
{}
template <typename T>
AIndex<T>::AIndex(const T* data, const AIndex<T>& aindex) :
AIndex<T>(aindex)
{
mCData = data;
}
template <typename T>
AIndex<T> AIndex<T>::operator+(Int n) const
{
AIndex<T> o = *this;
o += n;
return o;
}
template <typename T>
AIndex<T> AIndex<T>::operator-(Int n) const
{
AIndex<T> o = *this;
o -= n;
return o;
}
template <typename T>
const T& AIndex<T>::operator*() const
{
return mCData[IB::mPos];
}
template <typename T>
const T* AIndex<T>::operator->() const
{
return mCData + IB::mPos;
}
template <typename T>
BIndex<T>::BIndex(T* data, const RangePtr& range, SizeT lexpos) :
AIndex<T>(data, range, lexpos),
mData(data)
{}
template <typename T>
BIndex<T>::BIndex(T* data, const AIndex<T>& ai) :
AIndex<T>(data, ai),
mData(data)
{}
template <typename T>
BIndex<T> BIndex<T>::operator+(Int n) const
{
BIndex<T> o = *this;
o += n;
return o;
}
template <typename T>
BIndex<T> BIndex<T>::operator-(Int n) const
{
BIndex<T> o = *this;
o -= n;
return o;
}
template <typename T>
T& BIndex<T>::operator*()
{
return mData[IB::mPos];
}
template <typename T>
T* BIndex<T>::operator->()
{
return mData + IB::mPos;
}
}
#endif

View file

@ -0,0 +1,71 @@
// -*- C++ -*-
/**
@file include/array/aindex.h
@brief Array index declaration.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_aindex_h__
#define __cxz_aindex_h__
#include "ranges/range_base.h"
#include "ranges/index_base.h"
#include "ranges/xindex.h"
#include "ranges/yrange.h"
namespace CNORXZ
{
// AIndex (A = Array)
template <typename T>
class AIndex : public YIndex
{
public:
typedef YIndex::IB IB;
using YIndex::operator=;
DEFAULT_MEMBERS(AIndex);
AIndex(const T* data, const RangePtr& range, SizeT lexpos = 0);
AIndex(const T* data, const YIndex& yindex);
AIndex(const T* data, const AIndex<T>& aindex);
AIndex operator+(Int n) const;
AIndex operator-(Int n) const;
const T& operator*() const;
const T* operator->() const;
protected:
const T* mCData = nullptr;
};
// BIndex (because B comes after A...)
template <typename T>
class BIndex : public AIndex<T>
{
public:
typedef AIndex<T> AI;
typedef typename AI::IB IB;
DEFAULT_MEMBERS(BIndex);
BIndex(T* data, const RangePtr& range, SizeT pos = 0);
BIndex(T* data, const AIndex<T>& cci);
BIndex operator+(Int n) const;
BIndex operator-(Int n) const;
T& operator*();
T* operator->();
private:
T* mData = nullptr;
};
}
#endif

View file

@ -0,0 +1,15 @@
// -*- C++ -*-
/**
@file include/array/array.cc.h
@brief Array main header for template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "array_base.cc.h"
#include "marray.cc.h"
#include "aindex.cc.h"
#include "slice.cc.h"

17
src/include/array/array.h Normal file
View file

@ -0,0 +1,17 @@
// -*- C++ -*-
/**
@file include/array/array.h
@brief Array main header.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "array_base.h"
#include "marray.h"
#include "aindex.h"
#include "slice.h"
#include "array.cc.h"

View file

@ -0,0 +1,382 @@
// -*- C++ -*-
/**
@file include/array/array_base.cc.h
@brief Array base class template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_array_base_cc_h__
#define __cxz_array_base_cc_h__
#include "array_base.h"
#include "slice.h"
namespace CNORXZ
{
/*=======================================================+
| Implementations for CArrayBase member functions |
+=======================================================*/
template <typename T>
CArrayBase<T>::CArrayBase(const RangePtr& range) :
mRange(rangeCast<YRange>(range))
{}
template <typename T>
template <typename I, typename M>
const T& CArrayBase<T>::operator[](const IndexInterface<I,M>& i) const
{
if(formatIsTrivial()){
return data()[i.lex()];
}
else {
auto ai = itLex(i);
return *ai;
}
}
template <typename T>
template <typename I, typename M>
const T& CArrayBase<T>::at(const IndexInterface<I,M>& i) const
{
auto ai = itLexSave(i);
return *ai;
}
template <typename T>
template <class... Indices>
const T& CArrayBase<T>::operator[](const SPack<Indices...>& pack) const
{
if(formatIsTrivial()){
return data()[pack.lex()];
}
else {
auto ai = itLex(pack);
return *ai;
}
}
template <typename T>
template <class... Indices>
const T& CArrayBase<T>::at(const SPack<Indices...>& pack) const
{
auto ai = itLexSave(pack);
return *ai;
}
template <typename T>
const T& CArrayBase<T>::operator[](const DPack& pack) const
{
auto ai = itLex(pack);
return *ai;
}
template <typename T>
const T& CArrayBase<T>::at(const DPack& pack) const
{
auto ai = itLexSave(pack);
return *ai;
}
template <typename T>
template <typename I, typename M>
Sptr<CArrayBase<T>> CArrayBase<T>::sl(const IndexInterface<I,M>& begin,
const IndexInterface<I,M>& end) const
{
auto ai = itLexSave(begin);
auto aj = itLexSave(end);
return std::make_shared<CSlice<T>>(ai.prange(aj), this, ai.format(), ai.pos());
}
template <typename T>
SizeT CArrayBase<T>::size() const
{
return mRange->size();
}
template <typename T>
RangePtr CArrayBase<T>::range() const
{
return mRange;
}
template <typename T>
typename CArrayBase<T>::const_iterator CArrayBase<T>::begin() const
{
return this->cbegin();
}
template <typename T>
typename CArrayBase<T>::const_iterator CArrayBase<T>::end() const
{
return this->cend();
}
template <typename T>
template <class Index>
COpRoot<T,Index> CArrayBase<T>::operator()(const Sptr<Index>& i) const
{
if(formatIsTrivial()){
// assert that index format is trivial and has correct extensions
CXZ_ASSERT(i->formatIsTrivial(),
"got non-trivial index for container with trivial format");
this->checkFormatCompatibility(*i);
return coproot(*this, i);
}
else {
if(i->formatIsTrivial()){
// try to apply container format.
// if the reformat changes the index type in any manner
// the format is not applicable:
if constexpr(std::is_same<decltype(i->reformat( Vector<SizeT>(), Vector<SizeT>() )),Index>::value){
auto beg = begin();
auto aformat = beg.deepFormat();
auto amax = beg.deepMax();
auto fi = i->reformat( aformat, amax );
return coproot(*this, moveToPtr( fi ) );
}
else {
this->checkFormatCompatibility(*i);
return coproot(*this, i);
}
}
else {
// check if format is compatible
this->checkFormatCompatibility(*i);
return coproot(*this, i);
}
}
}
template <typename T>
template <class... Indices>
inline decltype(auto) CArrayBase<T>::operator()(const SPack<Indices...>& pack) const
{
return operator()(mindexPtr(pack));
}
template <typename T>
inline decltype(auto) CArrayBase<T>::operator()(const DPack& pack) const
{
return operator()(yindexPtr(pack));
}
/*=================================================================+
| Implementations for protected CArrayBase member functions |
+=================================================================*/
template <typename T>
template <class Acc>
typename CArrayBase<T>::const_iterator CArrayBase<T>::itLex(const Acc& acc) const
{
return begin() + acc.lex();
}
template <typename T>
template <class Acc>
typename CArrayBase<T>::const_iterator CArrayBase<T>::itLexSave(const Acc& acc) const
{
CXZ_ASSERT(acc.lex() < this->size(), "index out of range");
// check further compatibility of index/range format!!!
return begin() + acc.lex();
}
template <typename T>
template <class Acc>
void CArrayBase<T>::checkFormatCompatibility(const Acc& acc) const
{
auto j = begin();
CXZ_ASSERT(acc.lmax().val() == j.lmax().val(),
"got index of iteration space size = " << acc.lmax().val()
<< ", expected size = " << acc.lmax().val());
Vector<SizeT> f1 = toVec(acc.deepFormat());
Vector<SizeT> f2 = j.deepFormat();
std::sort(f1.begin(),f1.end());
std::sort(f2.begin(),f2.end());
SizeT i1 = 0;
SizeT i2 = 0;
CXZ_ASSERT(f1[i1] == f2[i2], "obtained format " << toString(f1)
<< ", which is incompatible to target format " << toString(f2));
++i1;
++i2;
while(i1 < f1.size() and i2 < f2.size()){
if(f1[i1] < f2[i2]) {
if(++i1 == f1.size()) break;
CXZ_ASSERT(f1[i1] <= f2[i2], "obtained format " << toString(f1)
<< ", which is incompatible to target format " << toString(f2));
}
else if(f1[i1] > f2[i2]) {
if(++i2 == f2.size()) break;
CXZ_ASSERT(f1[i1] >= f2[i2], "obtained format " << toString(f1)
<< ", which is incompatible to target format " << toString(f2));
}
else {
++i1;
++i2;
}
}
}
/*======================================================+
| Implementations for ArrayBase member functions |
+======================================================*/
template <typename T>
ArrayBase<T>::ArrayBase(const RangePtr& range) :
CArrayBase<T>(range)
{}
template <typename T>
template <typename I, typename M>
T& ArrayBase<T>::operator[](const IndexInterface<I,M>& i)
{
if(this->formatIsTrivial()){
return data()[i.lex()];
}
else {
auto ai = itLex(i);
return *ai;
}
}
template <typename T>
template <typename I, typename M>
T& ArrayBase<T>::at(const IndexInterface<I,M>& i)
{
auto ai = itLexSave(i);
return *ai;
}
template <typename T>
template <class... Indices>
T& ArrayBase<T>::operator[](const SPack<Indices...>& pack)
{
if(this->formatIsTrivial()){
return data()[pack.lex()];
}
else {
auto ai = itLex(pack);
return *ai;
}
}
template <typename T>
template <class... Indices>
T& ArrayBase<T>::at(const SPack<Indices...>& pack)
{
auto ai = itLexSave(pack);
return *ai;
}
template <typename T>
T& ArrayBase<T>::operator[](const DPack& pack)
{
auto ai = itLex(pack);
return *ai;
}
template <typename T>
T& ArrayBase<T>::at(const DPack& pack)
{
auto ai = itLexSave(pack);
return *ai;
}
template <typename T>
template <typename I, typename M>
Sptr<ArrayBase<T>> ArrayBase<T>::sl(const IndexInterface<I,M>& begin,
const IndexInterface<I,M>& end)
{
auto ai = itLexSave(begin);
auto aj = itLexSave(end);
return std::make_shared<Slice<T>>(ai.prange(aj), this, ai.format(), ai.pos());
}
template <typename T>
typename ArrayBase<T>::iterator ArrayBase<T>::begin()
{
return iterator(this->data(), this->cbegin());
}
template <typename T>
typename ArrayBase<T>::iterator ArrayBase<T>::end()
{
return iterator(this->data(), this->cend());
}
template <typename T>
template <class Index>
OpRoot<T,Index> ArrayBase<T>::operator()(const Sptr<Index>& i)
{
if(this->formatIsTrivial()){
// assert that index format is trivial and has correct extensions
CXZ_ASSERT(i->formatIsTrivial(),
"got non-trivial index for container with trivial format");
this->checkFormatCompatibility(*i);
return oproot(*this, i);
}
else {
if(i->formatIsTrivial()){
// try to apply container format.
// if the reformat changes the index type in any manner
// the format is not applicable:
if constexpr(std::is_same<decltype(i->reformat( Vector<SizeT>(), Vector<SizeT>() )),Index>::value){
auto beg = begin();
auto aformat = beg.deepFormat();
auto amax = beg.deepMax();
auto fi = i->reformat( aformat, amax );
return oproot(*this, moveToPtr( fi ) );
}
else {
this->checkFormatCompatibility(*i);
return oproot(*this, i);
}
}
else {
// check if format is compatible
this->checkFormatCompatibility(*i);
return oproot(*this, i);
}
}
}
template <typename T>
template <class... Indices>
inline decltype(auto) ArrayBase<T>::operator()(const SPack<Indices...>& pack)
{
return operator()(mindexPtr(pack));
}
template <typename T>
inline decltype(auto) ArrayBase<T>::operator()(const DPack& pack)
{
return operator()(yindexPtr(pack));
}
/*================================================================+
| Implementations for protected ArrayBase member functions |
+================================================================*/
template <typename T>
template <class Acc>
typename ArrayBase<T>::iterator ArrayBase<T>::itLex(const Acc& acc)
{
return begin() + acc.lex();
}
template <typename T>
template <class Acc>
typename ArrayBase<T>::iterator ArrayBase<T>::itLexSave(const Acc& acc)
{
CXZ_ASSERT(acc.lex() < this->size(), "index out of range");
// check further compatibility of index/range format!!!
return begin() + acc.lex();
}
}
#endif

View file

@ -0,0 +1,290 @@
// -*- C++ -*-
/**
@file include/array/array_base.h
@brief Array base class declarations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_array_base_h__
#define __cxz_array_base_h__
#include <cstdlib>
#include <vector>
#include <memory>
#include <algorithm>
#include "base/base.h"
#include "aindex.h"
#include "operation/op_types.h"
namespace CNORXZ
{
/** ****
Abstract container base class
only read access to the data
@tparam T data type
*/
template <typename T>
class CArrayBase
{
public:
typedef AIndex<T> const_iterator; /** const iterator type */
DEFAULT_MEMBERS(CArrayBase); /**< default constructors and assignments */
/** construct container on a range
@param range
*/
CArrayBase(const RangePtr& range);
/** default destructor */
virtual ~CArrayBase() = default;
/** const data element access
@tparam I index type
@tparam M meta data type
@param i index
*/
template <typename I, typename M>
const T& operator[](const IndexInterface<I,M>& i) const;
/** const data element access
performs compatibility checks
@tparam I index type
@tparam M meta data type
@param i index
*/
template <typename I, typename M>
const T& at(const IndexInterface<I,M>& i) const;
/** const data element access
@tparam I index type
@tparam M meta data type
@param pack static index pack
*/
template <class... Indices>
const T& operator[](const SPack<Indices...>& pack) const;
/** const data element access
performs compatibility checks
@tparam I index type
@tparam M meta data type
@param i static index pack
*/
template <class... Indices>
const T& at(const SPack<Indices...>& pack) const;
/** const data element access
@param pack index pack
*/
const T& operator[](const DPack& pack) const;
/** const data element access
performs compatibility checks
@param i index pack
*/
const T& at(const DPack& pack) const;
/** create hypercubic slice from this container
@tparam I type of index used to indicate slice edges
@tparam M index meta type
@param begin begin edge
@param end end edge
*/
template <typename I, typename M>
Sptr<CArrayBase<T>> sl(const IndexInterface<I,M>& begin,
const IndexInterface<I,M>& end) const;
/** create operation on this container
@tparam Index type of operation index
@param i operation index
*/
template <class Index>
COpRoot<T,Index> operator()(const Sptr<Index>& i) const;
/** create operation on this container
@tparam Indices types of operation indices
@param pack pack of operation index
*/
template <class... Indices>
inline decltype(auto) operator()(const SPack<Indices...>& pack) const;
/** create operation on this container
@param pack pack of operation index
*/
inline decltype(auto) operator()(const DPack& pack) const;
/** get pointer to container data */
virtual const T* data() const = 0;
/** get number of elements in the container */
virtual SizeT size() const;
/** get container range */
virtual RangePtr range() const;
/** get index pointing to first position */
virtual const_iterator begin() const;
/** get index pointing to position after last position */
virtual const_iterator end() const;
/** get index pointing to first position */
virtual const_iterator cbegin() const = 0;
/** get index pointing to position after last position */
virtual const_iterator cend() const = 0;
/** check if container views the data, i.e. it does not own it */
virtual bool isView() const = 0;
protected:
RangePtr mRange; /**< the container range */
/** Get valid data index.
Create well-formated index from index pack (unformatted)
or index using trivial format.
@tparam Acc index type or index pack type
@param acc index or index pack
*/
template <class Acc>
const_iterator itLex(const Acc& acc) const;
/** Get valid data index.
Create well-formated index from index pack (unformatted)
or index using trivial format.
Perform compatibility checks.
@tparam Acc index type or index pack type
@param acc index or index pack
*/
template <class Acc>
const_iterator itLexSave(const Acc& acc) const;
/** Perform compatibility checks
@tparam Acc index type or index pack type
@param acc index or index pack.
*/
template <class Acc>
void checkFormatCompatibility(const Acc& acc) const;
/** check if format is trivial
@return true if container is data owning array, else return
result of the corresponding container index
*/
virtual bool formatIsTrivial() const = 0;
};
/** ****
Abstract container base class
read and write access to the data
@tparam T data type
*/
template <typename T>
class ArrayBase : public CArrayBase<T>
{
public:
typedef CArrayBase<T> CAB;
typedef typename CAB::const_iterator const_iterator; /**< constant iterator type */
typedef BIndex<T> iterator; /**< read/write iterator type */
using CAB::operator[];
using CAB::operator();
using CAB::at;
using CAB::data;
using CAB::begin;
using CAB::end;
using CAB::cbegin;
using CAB::cend;
using CAB::sl;
DEFAULT_MEMBERS(ArrayBase); /**< default constructors and assignments */
/** construct a container on a range
*/
ArrayBase(const RangePtr& range);
/** @copydoc CArrayBase::operator[]()
*/
template <typename I, typename M>
T& operator[](const IndexInterface<I,M>& i);
/** @copydoc CArrayBase::at()
*/
template <typename I, typename M>
T& at(const IndexInterface<I,M>& i);
/** @copydoc CArrayBase::operator[]()
*/
template <class... Indices>
T& operator[](const SPack<Indices...>& pack);
/** @copydoc CArrayBase::at()
*/
template <class... Indices>
T& at(const SPack<Indices...>& pack);
/** @copydoc CArrayBase::operator[]()
*/
T& operator[](const DPack& pack);
/** @copydoc CArrayBase::at()
*/
T& at(const DPack& pack);
/** @copydoc CArrayBase::operator()()
*/
template <class Index>
OpRoot<T,Index> operator()(const Sptr<Index>& i);
/** @copydoc CArrayBase::operator()()
*/
template <class... Indices>
inline decltype(auto) operator()(const SPack<Indices...>& pack);
/** @copydoc CArrayBase::operator()()
*/
inline decltype(auto) operator()(const DPack& pack);
/** @copydoc CArrayBase::sl()
*/
template <typename I, typename M>
Sptr<ArrayBase<T>> sl(const IndexInterface<I,M>& begin,
const IndexInterface<I,M>& end);
/** @copydoc CArrayBase::data()
read/write access
*/
virtual T* data() = 0;
/** @copydoc CArrayBase::begin()
read/write access
*/
virtual iterator begin();
/** @copydoc CArrayBase::end()
read/write access
*/
virtual iterator end();
protected:
/** @copydoc CArrayBase::itLex()
*/
template <class Acc>
iterator itLex(const Acc& acc);
/** @copydoc CArrayBase::itLexSave()
*/
template <class Acc>
iterator itLexSave(const Acc& acc);
};
}
#endif

View file

@ -0,0 +1,105 @@
// -*- C++ -*-
/**
@file include/array/marray.cc.h
@brief MArray implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_marray_cc_h__
#define __cxz_marray_cc_h__
#include "marray.h"
namespace CNORXZ
{
/*=======================================================+
| Implementation of MArray public member functions |
+=======================================================*/
template <typename T>
MArray<T>::MArray(const RangePtr& range) :
ArrayBase<T>(range), mCont(range->size())
{}
template <typename T>
MArray<T>::MArray(const RangePtr& range, const Vector<T>& vec) :
ArrayBase<T>(range), mCont(vec)
{}
template <typename T>
MArray<T>::MArray(const RangePtr& range, Vector<T>&& vec) :
ArrayBase<T>(range), mCont(vec)
{}
template <typename T>
MArray<T>& MArray<T>::init(const RangePtr& range)
{
AB::mRange = rangeCast<YRange>(range);
mCont.resize(AB::mRange->size());
return *this;
}
template <typename T>
MArray<T>& MArray<T>::extend(const RangePtr& range)
{
if(AB::mRange == nullptr) {
return this->init(range);
}
MArray<T> tmp(AB::mRange->extend(range));
auto ei = this->end();
auto ti = tmp.begin();
// this is not very efficient; remove by sub-index operation once available:
for(auto ii = this->begin(); ii != ei; ++ii){
ti.at(ii.meta());
*ti = *ii;
}
*this = std::move(tmp);
return *this;
}
template <typename T>
const T* MArray<T>::data() const
{
return mCont.data();
}
template <typename T>
T* MArray<T>::data()
{
return mCont.data();
}
template <typename T>
typename MArray<T>::const_iterator MArray<T>::cbegin() const
{
return const_iterator(mCont.data(), AB::mRange);
}
template <typename T>
typename MArray<T>::const_iterator MArray<T>::cend() const
{
return const_iterator(mCont.data(), AB::mRange, mCont.size());
}
template <typename T>
bool MArray<T>::isView() const
{
return false;
}
/*==========================================================+
| Implementation of MArray protected member functions |
+==========================================================*/
template <typename T>
bool MArray<T>::formatIsTrivial() const
{
return true;
}
}
#endif

View file

@ -0,0 +1,58 @@
// -*- C++ -*-
/**
@file include/array/marray.h
@brief MArray declarations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_marray_h__
#define __cxz_marray_h__
#include "array_base.h"
namespace CNORXZ
{
/** ***
Generic multi-dimensional array class
This class owns the data that can be accessed through it
**/
template <typename T>
class MArray : public ArrayBase<T>
{
public:
typedef CArrayBase<T> AB;
typedef typename AB::const_iterator const_iterator;
using CArrayBase<T>::operator[];
using ArrayBase<T>::operator[];
DEFAULT_MEMBERS(MArray);
MArray(const RangePtr& range);
MArray(const RangePtr& range, const Vector<T>& vec);
MArray(const RangePtr& range, Vector<T>&& vec);
MArray& init(const RangePtr& range);
MArray& extend(const RangePtr& range);
virtual const T* data() const override;
virtual T* data() override;
virtual const_iterator cbegin() const override;
virtual const_iterator cend() const override;
virtual bool isView() const override;
SERIALIZATION_FUNCTIONS;
protected:
virtual bool formatIsTrivial() const override final;
private:
Vector<T> mCont;
};
}
#endif

View file

@ -0,0 +1,120 @@
// -*- C++ -*-
/**
@file include/array/slice.cc.h
@brief Slice implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_slice_cc_h__
#define __cxz_slice_cc_h__
#include "slice.h"
namespace CNORXZ
{
/*========================================================+
| Implementation of public CSlice member functions |
+========================================================*/
template <typename T>
CSlice<T>::CSlice(const RangePtr& range, const CArrayBase<T>* parent,
const YFormat& blockSizes, SizeT off) :
CArrayBase<T>(range),
mCParent(parent),
mBlockSizes(blockSizes),
mOff(off)
{}
template <typename T>
const T* CSlice<T>::data() const
{
return mCParent->data() + mOff;
}
template <typename T>
typename CSlice<T>::const_iterator CSlice<T>::cbegin() const
{
return const_iterator(data(),YIndex(AB::mRange, mBlockSizes, 0));
}
template <typename T>
typename CSlice<T>::const_iterator CSlice<T>::cend() const
{
return const_iterator(data(),YIndex(AB::mRange, mBlockSizes, AB::mRange->size()));
}
template <typename T>
bool CSlice<T>::isView() const
{
return true;
}
/*===========================================================+
| Implementation of protected CSlice member functions |
+===========================================================*/
template <typename T>
bool CSlice<T>::formatIsTrivial() const
{
return cbegin().formatIsTrivial();
}
/*=======================================================+
| Implementation of public Slice member functions |
+=======================================================*/
template <typename T>
Slice<T>::Slice(const RangePtr& range, ArrayBase<T>* parent,
const YFormat& blockSizes, SizeT off) :
ArrayBase<T>(range),
mParent(parent),
mBlockSizes(blockSizes),
mOff(off)
{}
template <typename T>
T* Slice<T>::data()
{
return mParent->data() + mOff;
}
template <typename T>
const T* Slice<T>::data() const
{
return mParent->data() + mOff;
}
template <typename T>
typename Slice<T>::const_iterator Slice<T>::cbegin() const
{
return const_iterator(data(),YIndex(AB::mRange, mBlockSizes, 0));
}
template <typename T>
typename Slice<T>::const_iterator Slice<T>::cend() const
{
return const_iterator(data(),YIndex(AB::mRange, mBlockSizes, AB::mRange->size()));
}
template <typename T>
bool Slice<T>::isView() const
{
return true;
}
/*==========================================================+
| Implementation of protected Slice member functions |
+==========================================================*/
template <typename T>
bool Slice<T>::formatIsTrivial() const
{
return cbegin().formatIsTrivial();
}
}
#endif

102
src/include/array/slice.h Normal file
View file

@ -0,0 +1,102 @@
// -*- C++ -*-
/**
@file include/array/slice.h
@brief Slice declarations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_slice_h__
#define __cxz_slice_h__
#include "base/base.h"
#include "array_base.h"
namespace CNORXZ
{
/** ****
constant and possibly partial view on the data
of another container
@tparam T data type
*/
template <typename T>
class CSlice : public CArrayBase<T>
{
public:
typedef CArrayBase<T> AB;
typedef typename AB::const_iterator const_iterator;
DEFAULT_MEMBERS(CSlice); /**< default constructors and assignments */
/** create slice from an array
@param range the slice's container range
@param parent the original container
@param blockSizes the format of the slice
@param off the initial pointer position w.r.t. the original initial position
*/
CSlice(const RangePtr& range, const CArrayBase<T>* parent,
const YFormat& blockSizes, SizeT off);
virtual const T* data() const override;
virtual const_iterator cbegin() const override;
virtual const_iterator cend() const override;
virtual bool isView() const override final;
protected:
virtual bool formatIsTrivial() const override final;
const CArrayBase<T>* mCParent = nullptr; /**< pointer to the original container */
YFormat mBlockSizes; /**< the format */
SizeT mOff = 0; /** pointer offset w.r.t. the original pointer */
};
/** ****
possibly partial view on the data
of another container
@tparam T data type
*/
template <typename T>
class Slice : public ArrayBase<T>
{
public:
typedef CArrayBase<T> AB;
typedef typename AB::const_iterator const_iterator;
DEFAULT_MEMBERS(Slice); /**< default constructors and assignments */
/** create slice from an array
@param range the slice's container range
@param parent the original container
@param blockSizes the format of the slice
@param off the initial pointer position w.r.t. the original initial position
*/
Slice(const RangePtr& range, ArrayBase<T>* parent,
const YFormat& blockSizes, SizeT off);
virtual const T* data() const override;
virtual T* data() override;
virtual const_iterator cbegin() const override;
virtual const_iterator cend() const override;
virtual bool isView() const override final;
protected:
virtual bool formatIsTrivial() const override final;
private:
ArrayBase<T>* mParent = nullptr;
YFormat mBlockSizes;
SizeT mOff = 0;
};
}
#endif

40
src/include/base/assert.h Normal file
View file

@ -0,0 +1,40 @@
// -*- C++ -*-
/**
@file include/base/assert.h
@brief warning and error makros
Definition of macros that can be used for convenient error handling and warnings
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include <iostream>
#include <sstream>
/** library error tag */
#define CXZ_ERRTAG __FILE__ << '@' << __LINE__ << '(' << __func__ << "): error"
/** library warning tag */
#define CXZ_WARNTAG __FILE__ << '@' << __LINE__ << ": warning"
/** throw error
@param errmsg error message
*/
#define CXZ_ERROR(errmsg) { \
auto mkerr = [&](){ std::stringstream ss; ss << CXZ_ERRTAG << ": " << errmsg << std::flush; return ss.str(); }; \
throw std::runtime_error(mkerr()); }
/** print warning
@param errmsg warning message
*/
#define CXZ_WARNING(errmsg) {\
std::cerr << CXZ_WARNTAG << ": " << errmsg << std::endl; }
/** throw error if given statement is not fulfilled
@param statement statement to be checked
@param errmsg error message
*/
#define CXZ_ASSERT(statement, errmsg) if(not (statement)) { CXZ_ERROR(errmsg); }

View file

@ -0,0 +1,18 @@
// -*- C++ -*-
/**
@file include/base/base.cc.h
@brief basic cc headers
Include basic cc headers containing defintions and macros
used throughout this library
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "dtype.cc.h"
#include "obj_handle.cc.h"
#include "to_string.cc.h"
#include "iter.cc.h"

38
src/include/base/base.h Normal file
View file

@ -0,0 +1,38 @@
// -*- C++ -*-
/**
@file include/base/base.h
@brief basic headers
Include basic headers containing defintions and macros
used throughout this library
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_base_h__
#define __cxz_base_h__
#include <cstdlib>
#include <iostream>
#include <utility>
#include "macros.h"
#include "assert.h"
#include "types.h"
#include "obj_handle.h"
#include "dtype.h"
#include "isq.h"
#include "iter.h"
#include "uuid.h"
#include "utils.h"
#include "config.h"
#include "intrin.h"
#include "base.cc.h"
#include "memory/memory.h"
#endif

35
src/include/base/config.h Normal file
View file

@ -0,0 +1,35 @@
// -*- C++ -*-
/**
@file include/base/config.h
@brief Runtime config functions declarations.
Declare functions returning version and configuration infos.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_config_h__
#define __cxz_config_h__
#include <cstdlib>
#include "base/types.h"
namespace CNORXZ
{
namespace Config
{
/** return cnorxz version */
String version();
/** return git hash */
String commit();
/** return compile flags */
String flags();
}
}
#endif

View file

@ -0,0 +1,74 @@
// -*- C++ -*-
/**
@file include/base/dtype.cc.h
@brief DType template member function definitions
Definitions of the template member functions of the DType class.
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_dtype_cc_h__
#define __cxz_dtype_cc_h__
#include <sstream>
#include "dtype.h"
#include "to_string.h"
namespace CNORXZ
{
// for tuple use vector<DType> !!!
// (yes DType is slow, thats why one should only use it for debugging)
template <typename T>
DType::DType(const T& d) : mD(d)
{
_mkToStr<T>();
_mkComp<T>();
}
template <typename T>
DType& DType::operator=(const T& d)
{
mD = d;
_mkToStr<T>();
_mkComp<T>();
return *this;
}
template <typename T>
void DType::_mkToStr()
{
mToStr = [](const std::any& d){
return toString(std::any_cast<T>(d));
};
}
template <typename T>
void DType::_mkComp()
{
mComp = [](const std::any& d, const std::any& a){
if(d.type() != a.type()){
return 2;
}
else {
auto& at = std::any_cast<const T&>(a);
auto& dt = std::any_cast<const T&>(d);
if(std::equal_to<T>{}(dt,at)){
return 0;
}
else if(std::less<T>{}(dt,at)){
return -1;
}
else {
return 1;
}
}
};
}
}
#endif

104
src/include/base/dtype.h Normal file
View file

@ -0,0 +1,104 @@
// -*- C++ -*-
/**
@file include/base/dtype.h
@brief DType declaration
DType is a generic type-erasing class that wrapps std::any.
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_dynamic_meta_h__
#define __cxz_dynamic_meta_h__
#include <cstdlib>
#include <utility>
#include <memory>
#include <any>
#include <functional>
#include "macros.h"
#include "types.h"
namespace CNORXZ
{
/** ****
Type erasing class wrapping std::any
*/
class DType
{
private:
std::any mD;
std::function<String(const std::any&)> mToStr;
std::function<Int(const std::any&,const std::any&)> mComp;
template <typename T>
void _mkToStr();
template <typename T>
void _mkComp();
public:
DEFAULT_MEMBERS(DType); /**< default constructors and assignments */
/** Generic constructor template
Constructs a DType from the given argument
@tparam T input data type
@param d input
*/
template <typename T>
DType(const T& d);
/** Generic assignment template
Assigns the given argument to the DType
@tparam T input data type
@param d input
*/
template <typename T>
DType& operator=(const T& d);
/** convert contained data so string */
String str() const { return mToStr(mD); }
/** return reference to type-erased data */
const std::any& get() const { return mD; }
/** check for equality
@param a variable to compare with
*/
bool operator==(const DType& a) const { return mComp(mD,a.mD) == 0; }
/** check for inequality
@param a variable to compare with
*/
bool operator!=(const DType& a) const { return mComp(mD,a.mD) != 0; }
/** check smaller
@param a variable to compare with
*/
bool operator<(const DType& a) const { return mComp(mD,a.mD) == -1; }
/** check greater
@param a variable to compare with
*/
bool operator>(const DType& a) const { return mComp(mD,a.mD) == 1; }
/** check not greater
@param a variable to compare with
*/
bool operator<=(const DType& a) const { auto c = mComp(mD,a.mD); return c <= 0; }
/** check not smaller
@param a variable to compare with
*/
bool operator>=(const DType& a) const { auto c = mComp(mD,a.mD); return c == 1 or c == 0; }
};
} // namespace CNORXZ
#endif

25
src/include/base/intrin.h Normal file
View file

@ -0,0 +1,25 @@
// -*- C++ -*-
/**
@file include/base/intrin.h
@brief Definitions related to intrinsics
**/
#ifndef __cxz_intrin_h__
#define __cxz_intrin_h__
#define MAX_VSIZE 1
// AVX:
#define AVX_BITS 256
#define AVX_VSIZE (AVX_BITS/8)
#ifdef CXZ_HAVE_AVX
#undef MAX_VSIZE
#define MAX_VSIZE AVX_VSIZE
#endif
// ...:
// ...
#endif

48
src/include/base/isq.h Normal file
View file

@ -0,0 +1,48 @@
// -*- C++ -*-
/**
@file include/base/isq.h
@brief Integer sequence range and creation functions
Declaration of integer sequence range and corresponding creating function templates
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_isq_h__
#define __cxz_isq_h__
#include <cstdlib>
#include <utility>
#include "types.h"
namespace CNORXZ
{
/** @cond 0 */
template <SizeT O, SizeT... Is>
std::index_sequence<(Is+O)...> mkIsqAdd(std::index_sequence<Is...> is) { return {}; }
template <SizeT B, SizeT E>
struct MkIsq
{
static auto make()
{
static_assert(B <= E, "begin of sequence must be smaller than end of sequence");
return mkIsqAdd<B>( std::make_index_sequence<E-B>{} );
}
typedef decltype(make()) type;
};
/** @endcond */
/** static consecutive integer sequence
@tparam B begin integer
@tparam E end integer
*/
template <SizeT B, SizeT E>
using Isqr = typename MkIsq<B,E>::type;
}
#endif

View file

@ -0,0 +1,69 @@
// -*- C++ -*-
/**
@file include/base/iter.cc.h
@brief Static for-loops
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_iter_cc_h__
#define __cxz_iter_cc_h__
#include "iter.h"
#include "xpr/func.h"
namespace CNORXZ
{
/** @cond 0 */
template <class G, class F, SizeT... Is>
constexpr decltype(auto) iteri(const G& g, const F& f, Isq<Is...> is)
{
if constexpr(std::is_same<F,NoF>::value){
( g(CSizeT<Is>{}), ... );
}
else {
return f( g(CSizeT<Is>{}) ... );
}
}
/** @endcond */
template <SizeT B, SizeT E, class G, class F>
constexpr decltype(auto) iter(const G& g, const F& f)
{
return iteri(g, f, Isqr<B,E>{});
}
/** @cond 0 */
template <SizeT E, SizeT I, class G, class F, class C, typename... Args>
constexpr decltype(auto) iterIfi(const G& g, const F& f, const C& c, const Args&... args)
{
if constexpr(I >= E){
if constexpr(std::is_same<F,NoF>::value){
return;
}
else {
return f(args...);
}
}
else {
if constexpr(c(CSizeT<I>{})){
return iterIfi<E,I+1>(g, f, c, args..., g(CSizeT<I>{}));
}
else {
return iterIfi<E,I+1>(g, f, c, args...);
}
}
}
/** @endcond */
template <SizeT B, SizeT E, class G, class F, class C>
constexpr decltype(auto) iterIf(const G& g, const F& f, const C& c)
{
return iterIfi<E,B>(g, f, c);
}
}
#endif

57
src/include/base/iter.h Normal file
View file

@ -0,0 +1,57 @@
// -*- C++ -*-
/**
@file include/base/iter.h
@brief Static for-loops
Declaration of function templates that can be used to implement a static for-loop
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_iter_h__
#define __cxz_iter_h__
#include <cstdlib>
#include "types.h"
namespace CNORXZ
{
/** @cond 0 */
template <class G, class F, SizeT... Is>
constexpr decltype(auto) iteri(const G& g, const F& f, Isq<Is...> is);
/** @endcond */
/** static for loop
@tparam B begin index
@tparam E end index
@tparam G type of expression to executed for each element
@tparam F type of accumulating expression collecting result for all elements
@param g expression to executed for each element
@param f accumulating expression collecting result for all elements
*/
template <SizeT B, SizeT E, class G, class F>
constexpr decltype(auto) iter(const G& g, const F& f);
/** @cond 0 */
template <SizeT E, SizeT I, class G, class F, class C, typename... Args>
constexpr decltype(auto) iterIfi(const G& g, const F& f, const C& c, const Args&... args);
/** @endcond */
/** static conditional for loop
@tparam B begin index
@tparam E end index
@tparam G type of expression to executed for each element
@tparam F type of accumulating expression collecting result for all elements
@tparam C type of condition expression
@param g expression to executed for each element
@param f accumulating expression collecting result for all elements
@param c condition expression
*/
template <SizeT B, SizeT E, class G, class F, class C>
constexpr decltype(auto) iterIf(const G& g, const F& f, const C& c);
}
#endif

135
src/include/base/macros.h Normal file
View file

@ -0,0 +1,135 @@
// -*- C++ -*-
/**
@file include/base/macros.h
@brief useful macros
Define useful macros that are used throughout this library for convenience,
briefnes and/or debugging.
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_macros_h__
#define __cxz_macros_h__
#include <iostream>
#ifndef CHECK
#define CHECK std::cout << __FILE__ << ": @" << __LINE__ << " in " << __func__ << std::endl;
#endif
#ifndef VCHECK
#define VCHECK(a) std::cout << __FILE__ << ": @" << __LINE__ \
<< " in " << __func__ << ": " << #a << " = " << a << std::endl;
#endif
/** shortcut for defining default constructor */
#define DEFAULT_C(__class_name__) __class_name__() = default
/** shortcut for defining default copy constructor */
#define DEFAULT_COPY_C(__class_name__) __class_name__(const __class_name__& a) = default
/** shortcut for defining default copy assignment */
#define DEFAULT_COPY_A(__class_name__) __class_name__& operator=(const __class_name__& a) = default
/** shortcut for defining default move constructor */
#define DEFAULT_MOVE_C(__class_name__) __class_name__(__class_name__&& a) = default
/** shortcut for defining default move assignment */
#define DEFAULT_MOVE_A(__class_name__) __class_name__& operator=(__class_name__&& a) = default
/** shortcut for defining default copy constructor and assignment */
#define DEFAULT_COPY(__class_name__) DEFAULT_COPY_C(__class_name__); DEFAULT_COPY_A(__class_name__)
/** shortcut for defining default move constructor and assignment */
#define DEFAULT_MOVE(__class_name__) DEFAULT_MOVE_C(__class_name__); DEFAULT_MOVE_A(__class_name__)
/** shortcut for defining default copy and move constructor and assignment */
#define DEFAULT_MEMBERS_X(__class_name__) DEFAULT_COPY(__class_name__); DEFAULT_MOVE(__class_name__)
/** shortcut for defining default constructor, default copy and move constructor and assignment */
#define DEFAULT_MEMBERS(__class_name__) DEFAULT_C(__class_name__); DEFAULT_MEMBERS_X(__class_name__)
/** shortcut for defining default constructor
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_C(__spec__,__class_name__) __spec__ __class_name__() = default
/** shortcut for defining default copy constructor
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_COPY_C(__spec__,__class_name__) __spec__ __class_name__(const __class_name__& a) = default
/** shortcut for defining default copy assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_COPY_A(__spec__,__class_name__) __spec__ __class_name__& operator=(const __class_name__& a) = default
/** shortcut for defining default move constructor
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_MOVE_C(__spec__,__class_name__) __spec__ __class_name__(__class_name__&& a) = default
/** shortcut for defining default move assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_MOVE_A(__spec__,__class_name__) __spec__ __class_name__& operator=(__class_name__&& a) = default
/** shortcut for defining default copy constructor and assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_COPY(__spec__,__class_name__) SP_DEFAULT_COPY_C(__spec__,__class_name__); SP_DEFAULT_COPY_A(__spec__,__class_name__)
/** shortcut for defining default move constructor and assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_MOVE(__spec__,__class_name__) SP_DEFAULT_MOVE_C(__spec__,__class_name__); SP_DEFAULT_MOVE_A(__spec__,__class_name__)
/** shortcut for defining default copy and move constructor and assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_MEMBERS_X(__spec__,__class_name__) SP_DEFAULT_COPY(__spec__,__class_name__); SP_DEFAULT_MOVE(__spec__,__class_name__)
/** shortcut for defining default constructor, default copy and move constructor and assignment
@param __spec__ specifier
@param __class_name__ class name
*/
#define SP_DEFAULT_MEMBERS(__spec__,__class_name__) SP_DEFAULT_C(__spec__,__class_name__); SP_DEFAULT_MEMBERS_X(__spec__,__class_name__)
/** shortcut for all typedefs needed to use a class as iterator
@param __meta_type__ meta data type
*/
#define INDEX_RANDOM_ACCESS_ITERATOR_DEFS(__meta_type__) typedef std::random_access_iterator_tag iterator_category; \
typedef SizeT difference_type; \
typedef __meta_type__ value_type; \
typedef const __meta_type__* pointer; \
typedef const __meta_type__& reference
#define CXZ_CVAL_FALSE static constexpr bool value = false
#define CXZ_CVAL_TRUE static constexpr bool value = true
#define IS_SAME(a,b) std::is_same<a,b>::value
#define IS_NOT_SAME(a,b) (not std::is_same<a,b>::value)
#ifdef HAVE_CEREAL
#define SERIALIZATION_FUNCTIONS template <class Archive> void save(Archive& ar, const std::uint32_t version) const; \
template <class Archive> void load(Archive& ar, const std::uint32_t version)
#define SERIALIZATION_FUNCTIONS_NOPUB friend class cereal::access; \
template <class Archive> void save(Archive& ar, const std::uint32_t version) const; \
template <class Archive> void load(Archive& ar, const std::uint32_t version)
#else
#define SERIALIZATION_FUNCTIONS static const int v = 0
#define SERIALIZATION_FUNCTIONS_NOPUB static const int v = 0
#endif
#endif

View file

@ -0,0 +1,74 @@
// -*- C++ -*-
/**
@file include/base/obj_handle.cc.h
@brief ObjHandle function definition
Implementation of the member functions of template ObjHandle
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_obj_handle_cc_h__
#define __cxz_obj_handle_cc_h__
#include "obj_handle.h"
namespace CNORXZ
{
template <typename T>
ObjHandle<T>::ObjHandle() {}
template <typename T>
ObjHandle<T>::ObjHandle(Uptr<T>&& a) : mC(std::forward<Uptr<T>>(a)) {}
template <typename T>
ObjHandle<T>::ObjHandle(const ObjHandle& a) : mC(a.mC->copy()) {}
template <typename T>
ObjHandle<T>::ObjHandle(ObjHandle&& a) : mC(a.mC) {}
template <typename T>
ObjHandle<T>& ObjHandle<T>::operator=(const ObjHandle& a)
{
mC = std::make_unique<T>(*a.mC);
return *this;
}
template <typename T>
ObjHandle<T>& ObjHandle<T>::operator=(ObjHandle&& a)
{
mC = a.mC;
return *this;
}
template <typename T>
T& ObjHandle<T>::operator*()
{
return *mC;
}
template <typename T>
T* ObjHandle<T>::operator->()
{
return &*mC;
}
template <typename T>
const T& ObjHandle<T>::operator*() const
{
return *mC;
}
template <typename T>
const T* ObjHandle<T>::operator->() const
{
return &*mC;
}
}
#endif

View file

@ -0,0 +1,84 @@
// -*- C++ -*-
/**
@file include/base/obj_handle.h
@brief ObjHandle template declaration
Pointer wrapper for directly handling objects via abstract base class;
Provides appropriate copy implementation
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_obj_handle_h__
#define __cxz_obj_handle_h__
#include "types.h"
namespace CNORXZ
{
/** ****
unique pointer wrapper
Allows to handle objects accessed through abstract base class pointers
as if they were complete (non-virtual) types.
Each type to be handled is required to have a copy() member function
that returns a copy of itself
@tparam T object type
*/
template <typename T>
class ObjHandle
{
protected:
Uptr<T> mC; /**< pointer to the object data */
public:
/** default constructor */
ObjHandle();
/** construct from unique pointer
@param a unique pointer
*/
ObjHandle(Uptr<T>&& a);
/** copy construct
@param a input
*/
ObjHandle(const ObjHandle& a);
/** move construct
@param a input
*/
ObjHandle(ObjHandle&& a);
/** copy assign
@param a input
*/
ObjHandle& operator=(const ObjHandle& a);
/** move assign
@param a input
*/
ObjHandle& operator=(ObjHandle&& a);
/** access data */
T& operator*();
/** get pointer to data */
T* operator->();
/** access data (const) */
const T& operator*() const;
/** get pointer to data (const) */
const T* operator->() const;
};
}
#endif

View file

@ -0,0 +1,113 @@
// -*- C++ -*-
/**
@file include/base/to_string.cc.h
@brief String converter implementation
Implementation of functions that convert a given object/type to a string
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_to_string_cc_h__
#define __cxz_to_string_cc_h__
#include "to_string.h"
#include "iter.h"
#include <sstream>
namespace CNORXZ
{
template <typename T>
String ToString<T>::func(const T& a)
{
std::stringstream ss;
ss << a;
return ss.str();
}
template <typename T>
String ToString<Vector<T>>::func(const Vector<T>& a)
{
std::stringstream ss;
ss << "[";
if(a.size() == 0){
ss << "]";
}
else {
auto it = a.begin();
for(; it != a.end()-1; ++it){
ss << toString(*it) << ",";
}
ss << toString(*it) << "]";
}
return ss.str();
}
template <typename T, size_t N>
String ToString<Arr<T,N>>::func(const Arr<T,N>& a)
{
std::stringstream ss;
ss << "(";
if constexpr(N == 0){
ss << ")";
}
else {
auto it = a.begin();
for(; it != a.end()-1; ++it){
ss << toString(*it) << ",";
}
ss << toString(*it) << ")";
}
return ss.str();
}
template <typename... Ts>
String ToString<Tuple<Ts...>>::func(const Tuple<Ts...>& t)
{
const String blim = "(";
const String elim = ")";
const String dlim = ",";
return iter<1,sizeof...(Ts)>
( [&](auto i) { return toString(std::get<i>(t)); },
[&](const auto&... xs) {
return blim + toString(std::get<0>(t)) + ( (dlim + xs) + ... ) + elim;
} );
}
template <typename T, typename S>
String ToString<std::pair<T,S>>::func(const std::pair<T,S>& p)
{
return String("(") + toString(p.first) + "," + toString(p.second) + ")";
}
template <typename T, typename S>
String ToString<std::map<T,S>>::func(const std::map<T,S>& p)
{
std::stringstream ss;
ss << "{";
if(p.size() == 0){
ss << "}";
}
else {
auto it = p.begin();
auto e = p.end();
e--;
for(; it != e; ++it){
ss << toString(it->first) << ":" << toString(it->second) << ",";
}
ss << toString(it->first) << ":" << toString(it->second) << "}";
}
return ss.str();
}
template <typename T>
String toString(const T& a)
{
return ToString<T>::func(a);
}
}
#endif

View file

@ -0,0 +1,135 @@
// -*- C++ -*-
/**
@file include/base/to_string.h
@brief String converter declarations.
Declaration of functions that convert a given object/type to a string.
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_to_string_h__
#define __cxz_to_string_h__
#include "types.h"
namespace CNORXZ
{
/** ***
Generic cast to string
@tparam T type to be casted
*/
template <typename T>
struct ToString
{
/** cast to string
@param a object to be casted
*/
static String func(const T& a);
};
/** ***
Specialization of ToString for strings
*/
template <>
struct ToString<String>
{
/** cast to string
@param a string to be casted
*/
static String func(const String& a);
};
/** ***
Specialization of ToString for vectors
@tparam T vector element type
*/
template <typename T>
struct ToString<Vector<T>>
{
/** cast to string
@param a vector to be casted
*/
static String func(const Vector<T>& a);
};
/** ***
Specialization of ToString for arrays
@tparam T array element type
@tparam N array size
*/
template <typename T, SizeT N>
struct ToString<Arr<T,N>>
{
/** cast to string
@param a array to be casted
*/
static String func(const Arr<T,N>& a);
};
/** ***
Specialization of ToString for tuples
@tparam Ts tuple element types
*/
template <typename... Ts>
struct ToString<Tuple<Ts...>>
{
/** cast to string
@param a tuple to be casted
*/
static String func(const Tuple<Ts...>& t);
};
/** ***
Specialization of ToString for pairs
@tparam T first element type
@tparam S second element type
*/
template <typename T, typename S>
struct ToString<std::pair<T,S>>
{
/** cast to string
@param a pair to be casted
*/
static String func(const std::pair<T,S>& t);
};
/** ***
Specialization of ToString for maps
@tparam T key type
@tparam S value type
*/
template <typename T, typename S>
struct ToString<std::map<T,S>>
{
/** cast to string
@param a map to be casted
*/
static String func(const std::map<T,S>& t);
};
/** ***
Specialization of ToString for DType
*/
template <>
struct ToString<DType>
{
/** cast to string
@param a DType to be casted
*/
static String func(const DType& a);
};
/** wrapper function for ToString
@tparam T type to be casted
@param a object to be casted
*/
template <typename T>
String toString(const T& a);
}
#endif

321
src/include/base/types.h Normal file
View file

@ -0,0 +1,321 @@
// -*- C++ -*-
/**
@file include/base/types.h
@brief Declaration of all library types
This file contains the declaration of all library types
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_types_h__
#define __cxz_types_h__
#include <string>
#include <vector>
#include <memory>
#include <tuple>
#include <complex>
#include <array>
#include <map>
#include <typeinfo>
#include <utility>
#include <numeric>
#include <cstdint>
namespace CNORXZ
{
/*====================+
| standard types |
=====================*/
typedef std::intptr_t PtrId;
typedef int32_t Int;
typedef int64_t LInt;
typedef uint64_t SizeT;
typedef double Double;
typedef Double Real;
typedef std::complex<Real> Complex;
typedef std::string String;
template <typename T, size_t N>
using Arr = std::array<T,N>;
template <typename T>
using Sptr = std::shared_ptr<T>;
template <typename T>
using Wptr = std::weak_ptr<T>;
template <typename T>
using Uptr = std::unique_ptr<T>;
template <typename T, typename U>
using Pair = std::pair<T,U>;
template <typename... T>
using Tuple = std::tuple<T...>;
template <SizeT I, typename... T>
using TupleElem = std::tuple_element<I,Tuple<T...>>;
template <typename T>
using RemoveRef = typename std::remove_reference<T>::type;
template <typename K, typename V>
using Map = std::map<K,V>;
typedef std::type_info TypeInfo;
template <SizeT... Is>
using Isq = std::index_sequence<Is...>;
// cxz helper functions/classes: -> isq.h
template <class... T>
using Isqf = std::index_sequence_for<T...>;
template <SizeT N>
using CSizeT = std::integral_constant<SizeT,N>;
/*===================+
| library types |
+===================*/
/*
Naming Prefixes:
D = Y = Dynamic
V = X = Virtual
S = Static
P = Partial = Sub
C = Classic
M = Multi (Index,Ranges) or !const (Container)
U = One(=Uni) dimensional
N = None = Null
E = Extension (SSE,AVX,etc dof)
T = Thread
R = Rank
A = (const) Array
B = (mutable) Array
F = Functional, Map,...
*/
// default template parameter
class None {};
// definition: base/dtype.h
class DType;
// definition: base/obj_handle.h
template <typename T>
class ObjHandle;
// definition: memory/allocator.h
template <typename T>
class Allocator;
// definition: xpr/vpos_type.h
class VPosBase;
// definition: xpr/vpos_type.h
template <class PosT>
class VPos;
// definition: xpr/vpos_type.h
template <class PosT>
class VPosRef;
// definition: xpr/pos_type.h
class UPos;
// definition: xpr/pos_type.h
template <SizeT N>
class SPos;
// definition: xpr/pos_type.h
class FPos;
// definition: xpr/pos_type.h
template <SizeT N, SizeT... Ms>
class SFPos;
// definition: xpr/pos_type.h
class DPos;
// definition: xpr/pos_type.h
class DPosRef;
// definition: xpr/pos_type.h
template <class PosT1, class PosT2>
class MPos;
// definition: ranges/range_base.h
class RangeBase;
typedef Sptr<RangeBase> RangePtr;
// definition: ranges/index_base.h
template <class I, typename MetaType>
class IndexInterface;
template <class I, typename MetaType>
using IndexPtr = Sptr<IndexInterface<I,MetaType>>;
// definition: ranges/nrange.h
class NRange; // null-range (range over none)
// definition: ranges/nrange.h
class NIndex;
// definition: ranges/urange.h
template <typename Meta>
class URange; // generic simple range (uni-dimensional)
// definition: ranges/urange.h
template <typename Meta>
class UIndex;
// definition: ranges/prange.h
template <class Range>
class PRange;
// definition: ranges/prange.h
template <class Index>
class PIndex;
// definition: ranges/crange.h
class CRange; // classic range, trivial meta data
// definition: ranges/crange.h
class CIndex;
// definition: ranges/srange.h
template <typename Meta, SizeT S>
class SRange; // generic static size range
// definition: ranges/srange.h
template <typename Meta, SizeT S>
class SIndex;
// definition: ranges/mrange.h
template <class... Ranges>
class MRange; // multi range
// definition: ranges/mrange.h
template <class BlockType, class... Indices>
class GMIndex;
template <class... Indices>
using MIndex = GMIndex<None,Indices...>;
// definition: ranges/xindex.h
class XIndexBase; // dynamic index wrapper
typedef Sptr<XIndexBase> XIndexPtr;
// definition: ranges/dindex.h
class DIndex;
// definition: ranges/yrange.h
class YRange; // dynamic multi range
// definition: ranges/yrange.h
class YIndex;
typedef Sptr<YIndex> YIndexPtr;
// definition: ranges/pindex.h
template <class Index>
class PIndex; // partial index (index over sub-ranges and permutations)
// there should be also a static analogue
// definition: ranges/lindex.h
template <class Index, SizeT L>
class LIndex;
// definition: ranges/index_pack.h
template <class... Indices>
class SPack;
// definition: ranges/index_pack.h
class DPack;
// definition: ranges/index_format.h
template <SizeT N>
class MFormat;
// definition: ranges/index_format.h
template <class... PosT>
class GMFormat;
// definition: ranges/index_format.h
class YFormat;
// definition: array/array_base.h
template <typename T>
class CArrayBase;
// definition: array/array_base.h
template <typename T>
class ArrayBase;
// definition: array/array.h
template <typename T>
class MArray;
// definition: array/slice.h
template <typename T>
class CSlice;
// definition: array/slice.h
template <typename T>
class Slice;
// definition: operation/op_types.h
template <class OpT>
class COpInterface;
// definition: operation/op_types.h
template <class OpT>
class OpInterface;
// definition: operation/op_types.h
template <typename T, class IndexT>
class COpRoot;
// definition: operation/op_types.h
template <typename T, class IndexT>
class OpCont;
// definition: operation/op_types.h
template <typename T, class IndexT>
class OpRoot;
// definition: operation/op_types.h
template <class F, class... Ops>
class Operation;
// definition: operation/op_types.h
template <class CXpr>
class Contraction;
/*===================+
| derived types |
+===================*/
template <typename T>
using Vector = std::vector<T,Allocator<T>>;
template <typename T, SizeT N, bool Static>
struct Container
{ typedef Vector<T> type; };
template <typename T, SizeT N>
struct Container<T,N,true>
{ typedef Arr<T,N> type; };
}
#endif

147
src/include/base/utils.h Normal file
View file

@ -0,0 +1,147 @@
// -*- C++ -*-
/**
@file include/base/utils.h
@brief utilities
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_utils_h__
#define __cxz_utils_h__
#include <cstdlib>
#include <algorithm>
#include "types.h"
namespace CNORXZ
{
template <typename T, SizeT N>
Vector<T> toVec(const Arr<T,N>& a)
{
return iter<0,N>( [&](auto i) { return std::get<i>(a); },
[](const auto&... e) { return Vector<T> { e... }; } );
}
template <typename T>
Vector<T> toVec(const Vector<T>& a)
{
return a;
}
template <typename T>
Vector<T> toVec(const T& a)
{
return Vector<T> { a };
}
template <typename T, SizeT N1, SizeT N2>
constexpr Arr<T,N1+N2> cat2(const Arr<T,N1>& a1, const Arr<T,N2>& a2)
{
return iter<0,N1+N2>
( [&](auto i) { if constexpr(i < N1) { return std::get<i>(a1); } else { return std::get<i-N1>(a2); } },
[](const auto&... e) { return Arr<T,N1+N2> { e... }; } );
}
template <typename T, SizeT N1>
constexpr Arr<T,N1+1> cat2(const Arr<T,N1>& a1, const T& a2)
{
return iter<0,N1>
( [&](auto i) { return std::get<i>(a1); },
[&](const auto&... e) { return Arr<T,N1+1> { e..., a2 }; } );
}
template <typename T, SizeT N1>
constexpr Arr<T,N1+1> cat2(const T& a1, const Arr<T,N1>& a2)
{
return iter<0,N1>
( [&](auto i) { return std::get<i>(a2); },
[&](const auto&... e) { return Arr<T,N1+1> { a1, e... }; } );
}
template <typename T>
constexpr Arr<T,2> cat2(const T& a1, const T& a2)
{
return Arr<T,2> { a1, a2 };
}
template <typename T, SizeT N2>
Vector<T> cat2(const Vector<T>& a1, const Arr<T,N2>& a2)
{
Vector<T> o(a1.size()+N2);
std::copy(a1.begin(), a1.end(), o.begin());
std::copy(a2.begin(), a2.end(), o.begin()+a1.size());
return o;
}
template <typename T, SizeT N1>
Vector<T> cat2(const Arr<T,N1>& a1, const Vector<T>& a2)
{
Vector<T> o(N1+a2.size());
std::copy(a1.begin(), a1.end(), o.begin());
std::copy(a2.begin(), a2.end(), o.begin()+N1);
return o;
}
template <typename T>
Vector<T> cat2(const Vector<T>& a1, const Vector<T>& a2)
{
Vector<T> o(a1.size()+a2.size());
std::copy(a1.begin(), a1.end(), o.begin());
std::copy(a2.begin(), a2.end(), o.begin()+a1.size());
return o;
}
template <typename T>
Vector<T> cat2(const Vector<T>& a1, const T& a2)
{
Vector<T> o(a1);
o.push_back(a2);
return o;
}
template <typename T, SizeT N1>
Vector<T> cat2(const T& a1, const Vector<T>& a2)
{
Vector<T> o { a1 };
o.insert(o.end(), a2.begin(), a2.end());
return o;
}
template <typename T1, typename T2, typename... Ts>
decltype(auto) concat(const T1& a1, const T2& a2, const Ts&... as)
{
if constexpr(sizeof...(Ts) != 0){
return cat2(a1, concat(a2, as...));
}
else {
return cat2(a1, a2);
}
}
template <typename T, SizeT N>
constexpr Arr<T,N> mul(const Arr<T,N>& a, const T& b)
{
return iter<0,N>( [&](auto i) { return std::get<i>(a) * b; },
[](const auto&... e) { return Arr<T,N> { e... }; } );
}
template <typename T>
Vector<T> mul(const Vector<T>& a, const T& b)
{
Vector<T> o(a.size());
std::transform(a.begin(), a.end(), o.begin(), [&](const auto& x) { return x*b; } );
return o;
}
template <typename T>
constexpr T mul(const T& a, const T& b)
{
return a*b;
}
}
#endif

87
src/include/base/uuid.h Normal file
View file

@ -0,0 +1,87 @@
// -*- C++ -*-
/**
@file include/base/uuid.h
@brief cnorxz uuid declaration.
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_uuid_h__
#define __cxz_uuid_h__
#include <stdint.h>
#include <functional>
namespace CNORXZ
{
/** ***
uuid
*/
struct Uuid
{
uint64_t i1; /**< first 8 bytes */
uint64_t i2; /**< second 8 bytes */
};
/** create new uuid */
Uuid mkUuid();
/** operator equal to
@param a left hand side
@param b right hand side
*/
inline bool operator==(const Uuid& a, const Uuid& b)
{
return a.i1 == b.i1 and a.i2 == b.i2;
}
/** operator not equal to
@param a left hand side
@param b right hand side
*/
inline bool operator!=(const Uuid& a, const Uuid& b)
{
return a.i1 != b.i1 or a.i2 != b.i2;
}
/** operator less than
@param a left hand side
@param b right hand side
*/
inline bool operator<(const Uuid& a, const Uuid& b)
{
return (a.i1 == b.i1) ? a.i2 < b.i2 : a.i1 < b.i1;
}
/** operator greater than
@param a left hand side
@param b right hand side
*/
inline bool operator>(const Uuid& a, const Uuid& b)
{
return (a.i1 == b.i1) ? a.i2 > b.i2 : a.i1 > b.i1;
}
/** operator less or equal
@param a left hand side
@param b right hand side
*/
inline bool operator<=(const Uuid& a, const Uuid& b)
{
return not( (a.i1 == b.i1) ? a.i2 > b.i2 : a.i1 > b.i1 );
}
/** operator greater or equal
@param a left hand side
@param b right hand side
*/
inline bool operator>=(const Uuid& a, const Uuid& b)
{
return not( (a.i1 == b.i1) ? a.i2 < b.i2 : a.i1 < b.i1 );
}
}
#endif

View file

@ -1,39 +0,0 @@
// -*- C++ -*-
#ifndef __cxz_base_def_h__
#define __cxz_base_def_h__
#include <cassert>
#define DEBUG_MODE_X
#ifdef DEBUG_MODE_X
#include <iostream>
#ifndef CHECK
#define CHECK std::cout << __FILE__ << ": @" << __LINE__ << " in " << __func__ << std::endl;
#endif
#ifndef VCHECK
#define VCHECK(a) std::cout << __FILE__ << ": @" << __LINE__ \
<< " in " << __func__ << ": " << #a << " = " << a << std::endl;
#endif
#else
#define CHECK
#define VCHECK(a)
#endif
#define DEFAULT_MEMBERS(__class_name__) __class_name__() = default; \
__class_name__(const __class_name__& in) = default; \
__class_name__& operator=(const __class_name__& in) = default; \
__class_name__(__class_name__&& in) = default; \
__class_name__& operator=(__class_name__&& in) = default
#define DEFAULT_MEMBERS_X(__class_name__) __class_name__(const __class_name__& in) = default; \
__class_name__& operator=(const __class_name__& in) = default; \
__class_name__(__class_name__&& in) = default; \
__class_name__& operator=(__class_name__&& in) = default
#endif

View file

@ -1,18 +0,0 @@
#ifndef __cxz_basic_types_h__
#define __cxz_basic_types_h__
#include <string>
namespace CNORXZ
{
// just to fix this forever:
typedef int32_t Int;
typedef uint64_t SizeT;
typedef double Double;
typedef Double Real;
typedef std::string String;
}
#endif

View file

@ -1,17 +1,16 @@
// -*- C++ -*-
/**
#include "ranges/ranges_header.cc.h" @file include/cnorxz.cc.h
@brief cnorxz main template header
#include "container_index.cc.h" Copyright (c) 2024 Christian Zimmermann. All rights reserved.
#include "cxz_operation.cc.h" Mail: chizeta@f3l.de
#include "functional_array.cc.h"
#include "helper_tools.cc.h"
#include "map_range.cc.h"
#include "cxz_array_base.cc.h"
#include "cxz_array.cc.h"
#include "slice.cc.h"
#include "dynamic_operation.cc.h"
#include "access.cc.h"
#include "op_expressions.cc.h"
//#include "high_level_operation.cc.h"
//#include "expressions.cc.h"
**/
#include "base/base.cc.h"
#include "memory/memory.cc.h"
#include "ranges/ranges.cc.h"
#include "array/array.cc.h"
#include "operation/operation.cc.h"

View file

@ -1,19 +1,22 @@
// -*- C++ -*- // -*- C++ -*-
/**
@file include/cnorxz.h
@brief cnorxz main header
Copyright (c) 2022 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_cnorxz_h__ #ifndef __cxz_cnorxz_h__
#define __cxz_cnorxz_h__ #define __cxz_cnorxz_h__
#include <cstdlib> #include "base/base.h"
#include "container_index.h" #include "memory/memory.h"
#include "cxz_operation.h" #include "ranges/ranges.h"
#include "cxz_array_base.h" #include "array/array.h"
#include "cxz_array.h" #include "operation/operation.h"
#include "functional_array.h"
#include "helper_tools.h"
#include "operation_def.h"
#include "map_range.h"
#include "dynamic_operation.h"
//#include "high_level_operation.h"
#include "cnorxz.cc.h" #include "cnorxz.cc.h"

View file

@ -1,440 +0,0 @@
#include "container_index.h"
namespace CNORXZ
{
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>::ConstContainerIndex(const ConstContainerIndex& in, bool copy) :
IB(in),
mNonTrivialBlocks(in.mNonTrivialBlocks),
mExternControl(false),
mBlockSizes(in.mBlockSizes),
mData(in.mData),
mObjPtrNum(in.mObjPtrNum),
mCPos(in.mCPos)
{
sfor_pn<0,sizeof...(Indices)>
( [&](auto i)
{
typedef typename std::remove_reference<decltype(*std::get<i>(mIPack))>::type
SubType;
std::get<i>(mIPack) = std::make_shared<SubType>( in.template get<i>() ) ;
return true;
});
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::copy(const ConstContainerIndex& in)
{
IB::operator=(in);
mNonTrivialBlocks = in.mNonTrivialBlocks;
mExternControl = false;
mBlockSizes = in.mBlockSizes;
mData = in.mData;
mObjPtrNum = in.mObjPtrNum;
mCPos = in.mCPos;
sfor_pn<0,sizeof...(Indices)>
( [&](auto i)
{
typedef typename std::remove_reference<decltype(*std::get<i>(mIPack))>::type
SubType;
std::get<i>(mIPack) = std::make_shared<SubType>( in.template get<i>() ) ;
return true;
});
return *this;
}
template <typename T, class... Indices>
template <class MRange>
ConstContainerIndex<T,Indices...>::ConstContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum) :
IndexInterface<ConstContainerIndex<T,Indices...>,std::tuple<typename Indices::MetaType...> >(range, 0),
mObjPtrNum(objPtrNum)
{
std::get<sizeof...(Indices)>(mBlockSizes) = 1;
sfor_mn<sizeof...(Indices),0>
( [&](auto i) {
auto r = range->template getPtr<i>();
std::get<i>(mIPack) = r->beginPtr();
*std::get<i>(mIPack) = 0;
std::get<i>(mBlockSizes) = sfor_p<i,sizeof...(Indices)>
( [&](auto j) { return std::get<j>(mIPack)->max(); } ,
[&](auto a, auto b) { return a * b; });
return 0;
});
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
}
template <typename T, class... Indices>
template <class MRange>
ConstContainerIndex<T,Indices...>::ConstContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum,
const std::array<size_t,sizeof...(Indices)+1>& blockSizes) :
IndexInterface<ConstContainerIndex<T,Indices...>,std::tuple<typename Indices::MetaType...> >(range, 0),
mObjPtrNum(objPtrNum)
{
sfor_mn<sizeof...(Indices),0>
( [&](auto i) {
auto r = range->template getPtr<i>();
std::get<i>(mIPack) = r->beginPtr();
*std::get<i>(mIPack) = 0;
return 0;
});
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
mNonTrivialBlocks = true;
}
template <typename T, class... Indices>
template <typename X>
ConstContainerIndex<T,Indices...>&
ConstContainerIndex<T,Indices...>::operator=(const ConstContainerIndex<X,Indices...>& in)
{
mIPack = in.mIPack;
return (*this)();
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::sync()
{
if(mExternControl){
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
}
return *this;
}
template <typename T, class... Indices>
template <size_t N>
auto& ConstContainerIndex<T,Indices...>::get() const
{
return *std::get<N>( mIPack );
}
template <typename T, class... Indices>
template <size_t N>
auto ConstContainerIndex<T,Indices...>::getPtr() const
{
return std::get<N>( mIPack );
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator()(const std::shared_ptr<Indices>&... inds)
{
return (*this)(std::make_tuple(inds...));
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator()(const std::tuple<std::shared_ptr<Indices>...>& inds)
{
sfor_pn<0,sizeof...(Indices)>
( [&](auto i) { std::get<i>(mIPack) = std::get<i>(inds); return 0; } );
mExternControl = true;
return sync();
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator()()
{
return sync();
}
template <typename T, class... Indices>
IndexType ConstContainerIndex<T,Indices...>::type() const { return IndexType::CONT; }
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator++()
{
if(mExternControl){
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
}
sfor_m<sizeof...(Indices),0>
( [&](auto i) {
auto& si = *std::get<i>( mIPack );
if(si.last() and i != 0) { si = 0; return true; }
else { ++si; return false; }
return false;
} );
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
++IB::mPos;
return *this;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator--()
{
if(mExternControl){
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
}
sfor_m<sizeof...(Indices),0>
( [&](auto i) {
auto& si = *std::get<i>( mIPack );
if(si.first() and i != 0) { si = si.max()-1; return true; }
else { --si; return false; }
return false;
} );
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
--IB::mPos;
return *this;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator=(size_t pos)
{
IB::mPos = pos;
RangeHelper::setIndexPack<sizeof...(Indices)-1>(mIPack, pos);
mCPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
return *this;
}
template <typename T, class... Indices>
int ConstContainerIndex<T,Indices...>::pp(std::intptr_t idxPtrNum)
{
const int tmp = RangeHelper::ppx<sizeof...(Indices)-1>(mIPack, mBlockSizes, idxPtrNum);
IB::mPos += tmp;
return tmp;
}
template <typename T, class... Indices>
int ConstContainerIndex<T,Indices...>::mm(std::intptr_t idxPtrNum)
{
const int tmp = RangeHelper::mmx<sizeof...(Indices)-1>(mIPack, mBlockSizes, idxPtrNum);
IB::mPos -= tmp;
return tmp;
}
template <typename T, class... Indices>
std::string ConstContainerIndex<T,Indices...>::stringMeta() const
{
return std::dynamic_pointer_cast<RangeType>( IB::mRangePtr )->stringMeta(IB::mPos);
}
template <typename T, class... Indices>
typename ConstContainerIndex<T,Indices...>::MetaType ConstContainerIndex<T,Indices...>::meta() const
{
MetaType metaTuple;
sfor_pn<0,sizeof...(Indices)>
( [&](auto i) { std::get<i>(metaTuple) = std::get<i>(mIPack)->meta(); return 0; } );
return metaTuple;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::at(const MetaType& metaPos)
{
sfor_pn<0,sizeof...(Indices)>
( [&](auto i) { std::get<i>(mIPack)->at( std::get<i>(metaPos) ); return 0; } );
IB::mPos = RangeHelper::makePos<sizeof...(Indices)-1>(mIPack, mBlockSizes);
return *this;
}
template <typename T, class... Indices>
size_t ConstContainerIndex<T,Indices...>::dim() const
{
return sizeof...(Indices);
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::first() const
{
return IB::pos() == 0;
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::last() const
{
return IB::pos() == IB::mMax - 1;
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::sliceMode() const
{
return mNonTrivialBlocks;
}
template <typename T, class... Indices>
std::shared_ptr<typename ConstContainerIndex<T,Indices...>::RangeType>
ConstContainerIndex<T,Indices...>::range()
{
return std::dynamic_pointer_cast<RangeType>( IB::mRangePtr );
}
template <typename T, class... Indices>
size_t ConstContainerIndex<T,Indices...>::getStepSize(size_t n)
{
if(n >= sizeof...(Indices)){
assert(0);
// throw !!
}
return mBlockSizes[n+1];
}
template <typename T, class... Indices>
template <class Exprs>
auto ConstContainerIndex<T,Indices...>::ifor(size_t step, Exprs exs) const
{
return RangeHelper::mkFor<0>(step, mIPack, mBlockSizes, exs);
}
template <typename T, class... Indices>
template <class Exprs>
auto ConstContainerIndex<T,Indices...>::iforh(size_t step, Exprs exs) const
{
return RangeHelper::mkForh<0>(step, mIPack, mBlockSizes, exs);
}
template <typename T, class... Indices>
template <class Exprs>
auto ConstContainerIndex<T,Indices...>::pifor(size_t step, Exprs exs) const
{
return RangeHelper::mkPFor<0>(step, mIPack, mBlockSizes, exs);
}
template <typename T, class... Indices>
std::intptr_t ConstContainerIndex<T,Indices...>::container() const
{
return mObjPtrNum;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::
format(const std::array<size_t,sizeof...(Indices)+1>& blocks)
{
mBlockSizes = blocks;
mNonTrivialBlocks = true;
return *this;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::setData(const T* data)
{
mData = data;
return *this;
}
template <typename T, class... Indices>
const T& ConstContainerIndex<T,Indices...>::operator*() const
{
return mData[mCPos];
}
template <typename T, class... Indices>
const T* ConstContainerIndex<T,Indices...>::operator->() const
{
return &mData[mCPos];
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...> ConstContainerIndex<T,Indices...>::operator++(int)
{
auto tmp = *this;
++(*this);
return tmp;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...> ConstContainerIndex<T,Indices...>::operator--(int)
{
auto tmp = *this;
--(*this);
return tmp;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator+=(int diff)
{
if(diff < 0){
for(int i = 0; i != diff; ++i){
(*this)--;
}
}
else {
for(int i = 0; i != diff; ++i){
(*this)++;
}
}
return *this;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...>& ConstContainerIndex<T,Indices...>::operator-=(int diff)
{
if(diff < 0){
for(int i = 0; i != diff; ++i){
(*this)++;
}
}
else {
for(int i = 0; i != diff; ++i){
(*this)--;
}
}
return *this;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...> ConstContainerIndex<T,Indices...>::operator+(int num) const
{
auto tmp = *this;
return tmp += num;
}
template <typename T, class... Indices>
ConstContainerIndex<T,Indices...> ConstContainerIndex<T,Indices...>::operator-(int num) const
{
auto tmp = *this;
return tmp -= num;
}
template <typename T, class... Indices>
int ConstContainerIndex<T,Indices...>::operator-(const ConstContainerIndex<T,Indices...>& it) const
{
return static_cast<int>( IB::mPos ) - static_cast<int>( it.pos() );
}
template <typename T, class... Indices>
const T& ConstContainerIndex<T,Indices...>::operator[](int num) const
{
return mData[IB::mPos + num];
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::operator<(const ConstContainerIndex<T,Indices...>& it) const
{
return IB::mPos < it.pos();
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::operator>(const ConstContainerIndex<T,Indices...>& it) const
{
return IB::mPos > it.pos();
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::operator<=(const ConstContainerIndex<T,Indices...>& it) const
{
return IB::mPos <= it.pos();
}
template <typename T, class... Indices>
bool ConstContainerIndex<T,Indices...>::operator>=(const ConstContainerIndex<T,Indices...>& it) const
{
return IB::mPos >= it.pos();
}
} // namespace CNORXZ

View file

@ -1,306 +0,0 @@
// -*- C++ -*-
#ifndef __cxz_container_index_h__
#define __cxz_container_index_h__
#include <cstdlib>
#include <tuple>
#include <memory>
#include "ranges/range_base.h"
#include "ranges/index_base.h"
#include "mbase_def.h"
#include "statics/static_for.h"
#include "ranges/range_helper.h"
namespace CNORXZ
{
template <typename T, class... Indices>
class ConstContainerIndex : public IndexInterface<ConstContainerIndex<T,Indices...>,
std::tuple<typename Indices::MetaType...> >
{
public:
typedef IndexInterface<ConstContainerIndex<T,Indices...>,
std::tuple<typename Indices::MetaType...> > IB;
typedef std::tuple<typename Indices::MetaType...> MetaType;
typedef std::tuple<std::shared_ptr<Indices>...> IndexPack;
typedef ContainerRange<typename Indices::RangeType...> RangeType;
static constexpr IndexType sType() { return IndexType::CONT; }
static constexpr size_t sDim() { return sizeof...(Indices); }
static constexpr size_t totalDim() { return (... * Indices::totalDim()); }
static constexpr SpaceType STYPE = SpaceType::ANY;
static constexpr bool PARALLEL = std::tuple_element<0,std::tuple<Indices...>>::type::PARALLEL;
template <typename X>
using CIX = ConstContainerIndex<X,Indices...>;
template <typename X>
friend class CIX;
private:
ConstContainerIndex() = default;
bool mNonTrivialBlocks = false;
bool mExternControl = false;
IndexPack mIPack;
std::array<size_t,sizeof...(Indices)+1> mBlockSizes;
const T* mData = nullptr;
std::intptr_t mObjPtrNum;
protected:
size_t mCPos;
public:
ConstContainerIndex(const ConstContainerIndex& in) = default;
ConstContainerIndex& operator=(const ConstContainerIndex& in) = default;
ConstContainerIndex(const ConstContainerIndex& in, bool copy);
ConstContainerIndex& copy(const ConstContainerIndex& in);
template <typename X>
ConstContainerIndex& operator=(const ConstContainerIndex<X,Indices...>& in);
template <class MRange>
ConstContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum);
template <class MRange>
ConstContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum,
const std::array<size_t,sizeof...(Indices)+1>& blockSizes);
template <size_t N>
size_t getBlockSize() const { return std::get<N>(mBlockSizes); }
const IndexPack& pack() const { return mIPack; }
ConstContainerIndex& sync(); // recalculate 'IB::mPos' when externalControl == true
ConstContainerIndex& operator()(const std::shared_ptr<Indices>&... inds); // control via external indices
ConstContainerIndex& operator()(const std::tuple<std::shared_ptr<Indices>...>& inds);
ConstContainerIndex& operator()(); // -> sync; just to shorten the code
// ==== >>>>> STATIC POLYMORPHISM <<<<< ====
IndexType type() const;
ConstContainerIndex& operator++();
ConstContainerIndex& operator--();
ConstContainerIndex& operator=(size_t pos);
int pp(std::intptr_t idxPtrNum);
int mm(std::intptr_t idxPtrNum);
std::string stringMeta() const;
MetaType meta() const;
ConstContainerIndex& at(const MetaType& metaPos);
size_t dim() const;
bool first() const;
bool last() const;
bool sliceMode() const;
std::shared_ptr<RangeType> range();
template <size_t N>
auto& get() const;
template <size_t N>
auto getPtr() const;
size_t getStepSize(size_t n);
template <class Exprs>
auto ifor(size_t step, Exprs exs) const;
template <class Exprs>
auto iforh(size_t step, Exprs exs) const;
template <class Exprs>
auto pifor(size_t step, Exprs exs) const;
std::intptr_t container() const;
ConstContainerIndex& format(const std::array<size_t,sizeof...(Indices)+1>& blocks);
// Iterator Stuff
ConstContainerIndex& setData(const T* data);
const T& operator*() const;
const T* operator->() const;
//T& operator*();
//T* operator->();
ConstContainerIndex operator++(int);
ConstContainerIndex operator--(int);
ConstContainerIndex& operator+=(int diff);
ConstContainerIndex& operator-=(int diff);
ConstContainerIndex operator+(int num) const;
ConstContainerIndex operator-(int num) const;
int operator-(const ConstContainerIndex& it) const;
const T& operator[](int num) const;
bool operator<(const ConstContainerIndex& it) const;
bool operator>(const ConstContainerIndex& it) const;
bool operator<=(const ConstContainerIndex& it) const;
bool operator>=(const ConstContainerIndex& it) const;
};
template <typename T, class... Indices>
class ContainerIndex : public ConstContainerIndex<T,Indices...>
{
public:
typedef ConstContainerIndex<T,Indices...> CCI;
typedef CCI IB;
typedef typename CCI::MetaType MetaType;
typedef typename CCI::IndexPack IndexPack;
typedef typename CCI::RangeType RangeType;
static constexpr IndexType sType() { return CCI::sType(); }
static constexpr size_t sDim() { return CCI::sDim(); }
static constexpr size_t totalDim() { return CCI::totalDim(); }
static constexpr SpaceType STYPE = CCI::STYPE;
static constexpr bool PARALLEL = CCI::PARALLEL;
template <typename X>
using CIX = ContainerIndex<X,Indices...>;
template <typename X>
friend class CIX;
private:
ContainerIndex() = default;
T* mMData = nullptr;
public:
ContainerIndex(const ContainerIndex& in) = default;
ContainerIndex& operator=(const ContainerIndex& in) = default;
ContainerIndex(const ContainerIndex& in, bool copy) : CCI(in,copy)
{ mMData = in.mMData; }
ContainerIndex(const ConstContainerIndex<T,Indices...>& in, T* data) : CCI(in)
{ mMData = data; }
ContainerIndex(const ConstContainerIndex<T,Indices...>& in, T* data, bool copy) :
CCI(in,copy)
{ mMData = data; }
ContainerIndex& copy(const ContainerIndex& in)
{ CCI::copy(in); mMData = in.mMData; }
template <typename X>
ContainerIndex& operator=(const ContainerIndex<X,Indices...>& in)
{ CCI::operator=(in); return *this; }
template <class MRange>
ContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum) : CCI(range, objPtrNum) {}
template <class MRange>
ContainerIndex(const std::shared_ptr<MRange>& range,
std::intptr_t objPtrNum,
const std::array<size_t,sizeof...(Indices)+1>& blockSizes)
: CCI(range, objPtrNum, blockSizes) {}
template <size_t N>
size_t getBlockSize() const { return CCI::template getBlockSize<N>(); }
const IndexPack& pack() const { CCI::pack(); return *this; }
ContainerIndex& sync() { return CCI::sync(); return *this; }
ContainerIndex& operator()(const std::shared_ptr<Indices>&... inds)
{ CCI::operator()(inds...); return *this; }
ContainerIndex& operator()(const std::tuple<std::shared_ptr<Indices>...>& inds)
{ CCI::operator()(inds); return *this; }
ContainerIndex& operator()() { CCI::operator()(); return *this; }
// ==== >>>>> STATIC POLYMORPHISM <<<<< ====
IndexType type() const { return CCI::type(); }
ContainerIndex& operator++() { CCI::operator++(); return *this; }
ContainerIndex& operator--() { CCI::operator--(); return *this; }
ContainerIndex& operator=(size_t pos) { CCI::operator=(pos); return *this; }
int pp(std::intptr_t idxPtrNum) { return CCI::pp(idxPtrNum); }
int mm(std::intptr_t idxPtrNum) { return CCI::mm(idxPtrNum); }
std::string stringMeta() const { return CCI::stringMeta; }
MetaType meta() const { return CCI::meta(); }
ContainerIndex& at(const MetaType& metaPos) { CCI::at(metaPos); return *this; }
size_t dim() const { return CCI::dim(); }
bool first() const { return CCI::first(); }
bool last() const { return CCI::last(); }
bool sliceMode() const { return CCI::sliceMode(); }
std::shared_ptr<RangeType> range() { return CCI::range(); }
template <size_t N>
auto& get() const { return CCI::template get<N>(); }
template <size_t N>
auto getPtr() const { return CCI::template getPtr<N>(); }
size_t getStepSize(size_t n) { return getStepSize(n); }
template <class Exprs>
auto ifor(size_t step, Exprs exs) const { return CCI::ifor(step, exs); }
template <class Exprs>
auto iforh(size_t step, Exprs exs) const { return CCI::iforh(step, exs); }
template <class Exprs>
auto pifor(size_t step, Exprs exs) const { return CCI::pifor(step, exs); }
std::intptr_t container() const { return CCI::container(); }
ContainerIndex& format(const std::array<size_t,sizeof...(Indices)+1>& blocks)
{ CCI::format(blocks); return *this; }
// Iterator Stuff
ContainerIndex& setData(T* data) { CCI::setData(data); mMData = data; return *this; }
const T& operator*() const { return CCI::operator*(); }
const T* operator->() const { return CCI::operator->(); }
T& operator*() { return mMData[CCI::mCPos]; }
T* operator->() { return &mMData[CCI::mCPos]; }
ContainerIndex operator++(int) { auto tmp = *this; ++(*this); return tmp; }
ContainerIndex operator--(int) { auto tmp = *this; --(*this); return tmp; }
ContainerIndex& operator+=(int diff) { CCI::operator+=(diff); return *this; }
ContainerIndex& operator-=(int diff) { CCI::operator-=(diff); return *this; }
ContainerIndex operator+(int num) const { CCI::operator+(num); return *this; }
ContainerIndex operator-(int num) const { CCI::operator-(num); return *this; }
int operator-(const ContainerIndex& it) const { return CCI::operator-(it); }
const T& operator[](int num) const { return CCI::operator[](num); }
bool operator<(const ContainerIndex& it) const { return CCI::operator<(it); }
bool operator>(const ContainerIndex& it) const { return CCI::operator>(it); }
bool operator<=(const ContainerIndex& it) const { return CCI::operator<=(it); }
bool operator>=(const ContainerIndex& it) const { return CCI::operator>=(it); }
};
} // end namespace CNORXZ
#endif

View file

@ -1,122 +0,0 @@
#ifndef __cxz_conversions_h__
#define __cxz_conversions_h__
#include "cxz_array.h"
#include "slice.h"
namespace CNORXZ
{
namespace ConversionSizes
{
template <size_t N>
struct OrigSize
{
template <typename C, typename T>
struct FromTo
{
static void check() { static_assert( not N % (sizeof(T) / sizeof(C)), "conversion does not fit" ); }
static constexpr size_t SIZE = N * sizeof(T) / sizeof(C);
};
};
template <>
struct OrigSize<MUI>
{
template <typename C, typename T>
struct FromTo
{
static void check() {}
static constexpr size_t SIZE = MUI;
};
};
}
namespace
{
template <typename C, typename T, size_t N>
using SC = typename ConversionSizes::OrigSize<N>::template FromTo<C,T>;
template <typename C, typename T, class Range>
using SCR = SC<C,T,Range::SIZE>;
template <typename C, typename T, class Range>
using SCRR = GenSingleRange<typename Range::MetaType,SpaceType::NONE,SCR<C,T,Range>::SIZE>;
}
template <size_t N>
struct SubTuple
{
template <class RTP, class... Ranges>
static inline auto mk(const RTP& rtp, const Ranges&... rs)
-> decltype(SubTuple<N-1>::mk(rtp, std::get<N>(rtp), rs...))
{
return SubTuple<N-1>::mk(rtp, std::get<N>(rtp), rs...);
}
};
template <>
struct SubTuple<0>
{
template <class RTP, class... Ranges>
static inline auto mk(const RTP& rtp, const Ranges&... rs)
-> decltype(std::make_tuple(std::get<0>(rtp), rs...))
{
return std::make_tuple(std::get<0>(rtp), rs...);
}
};
template <class... Ranges>
using LastR = typename std::tuple_element<sizeof...(Ranges)-1,std::tuple<Ranges...>>::type;
template <typename C, typename T, class... Ranges>
auto rtcast(const std::tuple<std::shared_ptr<Ranges>...>& rtp)
-> decltype(std::tuple_cat(SubTuple<sizeof...(Ranges)-2>::mk(rtp),
std::make_tuple( std::dynamic_pointer_cast<SCRR<C,T,LastR<Ranges...>>>
( SCRR<C,T,LastR<Ranges...>>::factory().create() ) ) ))
{
return std::tuple_cat(SubTuple<sizeof...(Ranges)-2>::mk(rtp),
std::make_tuple( std::dynamic_pointer_cast<SCRR<C,T,LastR<Ranges...>>>
( SCRR<C,T,LastR<Ranges...>>::factory().create() ) ) );
}
template <typename T, class... Ranges>
inline Slice<T,Ranges...> rangeTpToSlice( const std::tuple<std::shared_ptr<Ranges>...>& rtp, T* data )
{
return Slice<T,Ranges...>(rtp, data);
}
template <typename T, class... Ranges>
inline ConstSlice<T,Ranges...> rangeTpToSlice( const std::tuple<std::shared_ptr<Ranges>...>& rtp, const T* data )
{
return ConstSlice<T,Ranges...>(rtp, data);
}
template <typename C, typename T, class... Ranges>
auto tcast(Array<T,Ranges...>& ma)
-> decltype(rangeTpToSlice
( rtcast<C,T>( ma.range()->space() ),
reinterpret_cast<C*>( ma.data() ) ))
{
// VCHECK(reinterpret_cast<std::intptr_t>(ma.data()) % 32);
//VCHECK(reinterpret_cast<std::intptr_t>(reinterpret_cast<C*>(ma.data())) % 32);
return rangeTpToSlice
( rtcast<C,T>( ma.range()->space() ),
reinterpret_cast<C*>( ma.data() ) );
}
template <typename C, typename T, class... Ranges>
auto tcast(const Array<T,Ranges...>& ma)
-> decltype(rangeTpToSlice
( rtcast<C,T>( ma.range()->space() ),
reinterpret_cast<const C*>( ma.data() ) ))
{
//VCHECK(reinterpret_cast<std::intptr_t>(ma.data()) % 32);
//VCHECK(reinterpret_cast<std::intptr_t>(reinterpret_cast<C*>(ma.data())) % 32);
return rangeTpToSlice
( rtcast<C,T>( ma.range()->space() ),
reinterpret_cast<const C*>( ma.data() ) );
}
}
#endif

View file

@ -1,269 +0,0 @@
#include "cxz_array.h"
#include "statics/static_for.h"
namespace CNORXZ
{
template <typename T>
Scalar<T> scalar(const T& in)
{
NullRF nrf;
return Scalar<T>( std::dynamic_pointer_cast<NullRange>( nrf.create() ), vector<T>( { in } ) );
}
/*******************
* Array *
*******************/
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const typename CRange::Space& space) :
MutableArrayBase<T,SRanges...>(space),
mCont(MAB::mRange->size())
{
MAB::mInit = true;
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const typename CRange::Space& space,
const vector<T>& vec) :
MutableArrayBase<T,SRanges...>(space),
mCont(vec)
{
MAB::mInit = true;
if(mCont.size() > MAB::mRange->size()){
mCont.erase(mCont.begin() + MAB::mRange->size(), mCont.end());
}
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const std::shared_ptr<SRanges>&... ranges) :
MutableArrayBase<T,SRanges...>(ranges...),
mCont(MAB::mRange->size())
{
MAB::mInit = true;
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const std::shared_ptr<SRanges>&... ranges, const T& val) :
MutableArrayBase<T,SRanges...>(ranges...),
mCont(MAB::mRange->size(), val)
{
MAB::mInit = true;
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const std::shared_ptr<SRanges>&... ranges, const vector<T>& vec) :
MutableArrayBase<T,SRanges...>(ranges...),
mCont(vec)
{
MAB::mInit = true;
if(mCont.size() > MAB::mRange->size()){
mCont.erase(mCont.begin() + MAB::mRange->size(), mCont.end());
}
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(const std::shared_ptr<SRanges>&... ranges, vector<T>&& vec) :
MutableArrayBase<T,SRanges...>(ranges...),
mCont(std::forward<vector<T>>(vec))
{
MAB::mInit = true;
if(mCont.size() > MAB::mRange->size()){
mCont.erase(mCont.begin() + MAB::mRange->size(), mCont.end());
}
}
template <typename T, class... SRanges>
template <class... Ranges>
Array<T,SRanges...>::Array(const std::shared_ptr<SRanges>&... ranges, Array<T,Ranges...>&& in) :
MutableArrayBase<T,SRanges...>(ranges...),
mCont( std::move( in.mCont ) )
{
// maybe some checks here in the future...
assert(mCont.size() == MAB::mRange->size());
MAB::mInit = true;
in.mInit = false;
}
template <typename T, class... SRanges>
Array<T,SRanges...>::Array(Array<T,AnonymousRange>&& ama, SIZET<SRanges>... sizes) :
MutableArrayBase<T,SRanges...>
( ama.range()->template get<0>().template scast<SRanges...>(sizes...)->space() ),
mCont( std::move( ama.mCont ) )
{
MAB::mInit = true;
ama.mInit = false;
}
template <typename T, class... SRanges>
T& Array<T,SRanges...>::operator[](const IndexType& i)
{
return mCont[ i.pos() ];
}
template <typename T, class... SRanges>
const T& Array<T,SRanges...>::operator[](const IndexType& i) const
{
return mCont[ i.pos() ];
}
template <typename T, class... SRanges>
T& Array<T,SRanges...>::at(const typename IndexType::MetaType& meta)
{
return mCont[ MAB::cbegin().at(meta).pos() ];
}
template <typename T, class... SRanges>
const T& Array<T,SRanges...>::at(const typename IndexType::MetaType& meta) const
{
return mCont[ MAB::cbegin().at(meta).pos() ];
}
template <typename T, class... SRanges>
bool Array<T,SRanges...>::isConst() const
{
return false;
}
template <typename T, class... SRanges>
bool Array<T,SRanges...>::isSlice() const
{
return false;
}
template <typename T, class... SRanges>
template <class... SRanges2>
Array<T,SRanges2...> Array<T,SRanges...>::format(const std::shared_ptr<SRanges2>&... nrs)
{
//MAB::mInit = false;
return Array<T,SRanges2...>( nrs... , mCont );
}
template <typename T, class... SRanges>
template <class... SRanges2>
Array<T,SRanges2...> Array<T,SRanges...>::format(const std::tuple<std::shared_ptr<SRanges2>...>& nrs)
{
//MAB::mInit = false;
return Array<T,SRanges2...>( nrs , mCont );
}
template <typename T, class... SRanges>
template <class... SRanges2>
Slice<T,SRanges2...> Array<T,SRanges...>::slformat(const std::shared_ptr<SRanges2>&... nrs)
{
return Slice<T,SRanges2...>( nrs..., mCont.data() );
}
template <typename T, class... SRanges>
template <class... SRanges2>
ConstSlice<T,SRanges2...> Array<T,SRanges...>::slformat(const std::shared_ptr<SRanges2>&... nrs) const
{
return ConstSlice<T,SRanges2...>( nrs..., mCont.data() );
}
template <typename T, class... SRanges>
const T* Array<T,SRanges...>::data() const
{
return mCont.data();
}
template <typename T, class... SRanges>
T* Array<T,SRanges...>::data()
{
return mCont.data();
}
template <typename T, class... SRanges>
std::shared_ptr<ArrayBase<T,AnonymousRange> > Array<T,SRanges...>::anonymous(bool slice) const
{
AnonymousRangeFactory arf(MAB::mRange->space());
if(slice){
return std::make_shared<ConstSlice<T,AnonymousRange> >
( std::dynamic_pointer_cast<AnonymousRange>( arf.create() ),
data() );
}
else {
return std::make_shared<Array<T,AnonymousRange> >
( std::dynamic_pointer_cast<AnonymousRange>( arf.create() ),
mCont );
}
}
template <typename T, class... SRanges>
Array<T,SRanges...>& Array<T,SRanges...>::operator=(const T& in)
{
for(auto& x: mCont){
x = in;
}
return *this;
}
template <typename T, class... SRanges>
Array<T,SRanges...>& Array<T,SRanges...>::operator+=(const Array& in)
{
if(not MAB::mInit){ // not initialized by default constructor !!
(*this) = in;
}
else {
sfor_p<0,sizeof...(SRanges),0>
( [&](auto i) { return std::get<i>(MAB::mRange->space()).get() == std::get<i>(in.mRange->space()).get(); },
[&](auto a, auto b) { return a and b; });
for(size_t i = 0; i != mCont.size(); ++i){
mCont[i] += in.mCont[i];
}
}
return *this;
}
template <typename T, class... SRanges>
Array<T,SRanges...>& Array<T,SRanges...>::operator-=(const Array& in)
{
if(not MAB::mInit){ // not initialized by default constructor !!
(*this) = in;
}
else {
sfor_p<0,sizeof...(SRanges),0>
( [&](auto i) { return std::get<i>(MAB::mRange->space()).get() == std::get<i>(in.mRange->space()).get(); },
[&](auto a, auto b) { return a and b; });
for(size_t i = 0; i != mCont.size(); ++i){
mCont[i] -= in.mCont[i];
}
}
return *this;
}
template <typename T, class... SRanges>
Array<T,SRanges...>& Array<T,SRanges...>::operator*=(const T& in)
{
for(auto& x: mCont){
x *= in;
}
return *this;
}
template <typename T, class... SRanges>
Array<T,SRanges...>& Array<T,SRanges...>::operator/=(const T& in)
{
for(auto& x: mCont){
x /= in;
}
return *this;
}
template <typename T, class... SRanges>
Array<T,SRanges...>::operator T() const
{
//static_assert( sizeof...(SRanges) == 1, "try to cast non-scalar type into scalar" );
// TODO: check that SIZE is statically = 1 !!!
return mCont[0];
}
template <typename T, class... SRanges>
auto Array<T,SRanges...>::cat() const
-> decltype(ArrayCatter<T>::cat(*this))
{
return ArrayCatter<T>::cat(*this);
}
}

View file

@ -1,151 +0,0 @@
// -*- C++ -*-
#ifndef __cxz_array_h__
#define __cxz_array_h__
#include <algorithm>
#include "cxz_array_base.h"
#include "ranges/anonymous_range.h"
namespace CNORXZ
{
template <typename T>
struct ArrayCatter;
template <typename T>
struct ArrayCatter
{
template <class... Ranges>
static auto cat(const Array<T,Ranges...>& ma)
-> Array<T,Ranges...>
{
return ma;
}
};
template <typename T, class... SRanges>
class Array : public MutableArrayBase<T,SRanges...>
{
public:
typedef ContainerRange<SRanges...> CRange;
typedef ArrayBase<T,SRanges...> MAB;
typedef ConstContainerIndex<T,typename SRanges::IndexType...> IndexType;
using ArrayBase<T,SRanges...>::operator[];
using MutableArrayBase<T,SRanges...>::operator[];
DEFAULT_MEMBERS(Array);
Array(const std::shared_ptr<SRanges>&... ranges);
Array(const std::shared_ptr<SRanges>&... ranges, const T& val);
Array(const std::shared_ptr<SRanges>&... ranges, const vector<T>& vec);
Array(const std::shared_ptr<SRanges>&... ranges, vector<T>&& vec);
template <class... Ranges>
Array(const std::shared_ptr<SRanges>&... ranges, Array<T,Ranges...>&& in); // same effect as format
Array(const typename CRange::Space& space);
Array(const typename CRange::Space& space, const vector<T>& vec);
Array(Array<T,AnonymousRange>&& ama, SIZET<SRanges>... sizes);
// Only if ALL ranges have default extensions:
//Array(const vector<T>& vec);
//Array(vector<T>&& vec);
// template <class Range2, class Range3>
// Array(const Array<Array<T,Range2>,Range3> in);
// implement contstructor using FunctionalArray as Input !!!
//template <class Range2, class Range3>
//Array& operator=(const Array<Array<T,Range2>,Range3> in);
virtual T& operator[](const IndexType& i) final;
virtual const T& operator[](const IndexType& i) const final;
virtual T& at(const typename IndexType::MetaType& meta) override;
virtual const T& at(const typename IndexType::MetaType& meta) const override;
virtual bool isConst() const override;
virtual bool isSlice() const override;
template <class... SRanges2>
Array<T,SRanges2...> format(const std::shared_ptr<SRanges2>&... nrs); // reformat array using 'nr' which in
// total must have the same size as mRange
template <class... SRanges2>
Array<T,SRanges2...> format(const std::tuple<std::shared_ptr<SRanges2>...>& nrs);
template <class... SRanges2>
Slice<T,SRanges2...> slformat(const std::shared_ptr<SRanges2>&... nrs);
template <class... SRanges2>
ConstSlice<T,SRanges2...> slformat(const std::shared_ptr<SRanges2>&... nrs) const;
virtual const T* data() const override;
virtual T* data() override;
virtual vector<T>& vdata() { return mCont; }
virtual const vector<T>& vdata() const { return mCont; }
vector<T>&& vmove() { MAB::mInit = false; return std::move(mCont); }
virtual std::shared_ptr<ArrayBase<T,AnonymousRange> > anonymous(bool slice = false) const override;
//virtual std::shared_ptr<ArrayBase<T,AnonymousRange> > anonymousMove() override;
auto cat() const
-> decltype(ArrayCatter<T>::cat(*this));
operator T() const;
Array& operator=(const T& in);
Array& operator+=(const Array& in);
Array& operator-=(const Array& in);
Array& operator*=(const T& in);
Array& operator/=(const T& in);
template <typename U, class... SRanges2>
friend class Array;
private:
vector<T> mCont;
};
template <typename T>
using Scalar = Array<T,NullRange>;
template <typename T>
Scalar<T> scalar(const T& in);
template <typename T, class... ERanges>
struct ArrayCatter<Array<T,ERanges...> >
{
template <class... Ranges>
static auto cat(const Array<Array<T,ERanges...>,Ranges...>& ma)
-> Array<T,Ranges...,ERanges...>
{
auto sma = *ma.begin();
const size_t smas = sma.size();
const size_t mas = ma.size();
auto cr = ma.range()->cat(sma.range());
vector<T> ov;
ov.reserve(mas * smas);
for(auto& x: ma){
assert(x.size() == smas);
ov.insert(ov.end(), x.vdata().begin(), x.vdata().end());
}
return Array<T,Ranges...,ERanges...>(cr->space(), std::move(ov));
}
};
}
/* ========================= *
* --- TEMPLATE CODE --- *
* ========================= */
#endif

View file

@ -1,274 +0,0 @@
#include "cxz_array_base.h"
namespace CNORXZ
{
/**********************
* ArrayBase *
**********************/
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>::ArrayBase(const ArrayBase& in) :
mInit(in.mInit),
mRange(in.mRange)
{
if(mRange){
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
}
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>::ArrayBase(ArrayBase&& in) :
mInit(in.mInit),
mRange(in.mRange)
{
if(mRange){
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
}
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>& ArrayBase<T,SRanges...>::operator=(const ArrayBase& in)
{
mInit = in.mInit;
mRange = in.mRange;
if(mRange){
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
return *this;
}
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>& ArrayBase<T,SRanges...>::operator=(ArrayBase&& in)
{
mInit = in.mInit;
mRange = in.mRange;
if(mRange){
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
return *this;
}
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>::ArrayBase(const std::shared_ptr<SRanges>&... ranges)
{
ContainerRangeFactory<SRanges...> crf(ranges...);
mRange = std::dynamic_pointer_cast<ContainerRange<SRanges...> >( crf.create() );
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
template <typename T, class... SRanges>
ArrayBase<T,SRanges...>::ArrayBase(const typename CRange::Space& space)
{
ContainerRangeFactory<SRanges...> crf(space);
mRange = std::dynamic_pointer_cast<ContainerRange<SRanges...> >( crf.create() );
mProtoI = std::make_shared<IndexType>( mRange, reinterpret_cast<std::intptr_t>(this) );
}
template <typename T, class... SRanges>
template <typename X>
const T& ArrayBase<T,SRanges...>::operator[](const ConstContainerIndex<X,typename SRanges::IndexType...>& i)
{
IndexType ii(*mProtoI);
ii = i;
return (*this)[ii];
}
template <typename T, class... SRanges>
const T& ArrayBase<T,SRanges...>::operator[](const std::tuple<IPTR<typename SRanges::IndexType>...>& is) const
{
IndexType ii(*mProtoI);
ii(is);
return (*this)[ii];
}
template <typename T, class... SRanges>
size_t ArrayBase<T,SRanges...>::size() const
{
return mRange->size();
}
template <typename T, class... SRanges>
typename ArrayBase<T,SRanges...>::CIndexType ArrayBase<T,SRanges...>::begin() const
{
return cbegin();
}
template <typename T, class... SRanges>
typename ArrayBase<T,SRanges...>::CIndexType ArrayBase<T,SRanges...>::end() const
{
return end();
}
template <typename T, class... SRanges>
typename ArrayBase<T,SRanges...>::CIndexType ArrayBase<T,SRanges...>::cbegin() const
{
CIndexType i(*mProtoI,true);
i = 0;
return i.setData(data());
}
template <typename T, class... SRanges>
typename ArrayBase<T,SRanges...>::CIndexType ArrayBase<T,SRanges...>::cend() const
{
CIndexType i(*mProtoI,true);
i = i.max();
return i.setData(data());
}
template <typename T, class... SRanges>
const std::shared_ptr<typename ArrayBase<T,SRanges...>::CRange>&
ArrayBase<T,SRanges...>::range() const
{
return mRange;
}
template <typename T, class... SRanges>
bool ArrayBase<T,SRanges...>::isConst() const
{
return true;
}
template <typename T, class... SRanges>
ConstOperationRoot<T,SRanges...>
ArrayBase<T,SRanges...>::operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const
{
return ConstOperationRoot<T,SRanges...>(*this, inds...);
}
template <typename T, class... SRanges>
ConstOperationRoot<T,SRanges...>
ArrayBase<T,SRanges...>::op(const std::shared_ptr<CIndexType>& ind) const
{
return ConstOperationRoot<T,SRanges...>(data(), *ind);
}
template <typename T, class... SRanges>
template <class... MappedRanges>
ConstOperationRoot<T,MappedRanges...>
ArrayBase<T,SRanges...>::m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds) const
{
static_assert(sizeof...(SRanges) == sizeof...(MappedRanges),
"number of mapped ranges must be equal to number of original ranges");
return ConstOperationRoot<T,MappedRanges...>(*this, inds...);
}
template <typename T, class... SRanges>
bool ArrayBase<T,SRanges...>::isInit() const
{
return mInit;
}
template <typename T, class... SRanges>
template <size_t N>
auto ArrayBase<T,SRanges...>::getRangePtr() const
-> decltype(mRange->template getPtr<N>())
{
return mRange->template getPtr<N>();
}
/******************************
* MutableArrayBase *
******************************/
template <typename T, class... SRanges>
MutableArrayBase<T,SRanges...>::MutableArrayBase(const std::shared_ptr<SRanges>&... ranges) :
ArrayBase<T,SRanges...>(ranges...) {}
template <typename T, class... SRanges>
MutableArrayBase<T,SRanges...>::MutableArrayBase(const typename CRange::Space& space) :
ArrayBase<T,SRanges...>(space) {}
template <typename T, class... SRanges>
template <typename X>
T& MutableArrayBase<T,SRanges...>::operator[](const ConstContainerIndex<X,typename SRanges::IndexType...>& i)
{
IndexType ii(*MAB::mProtoI);
ii = i;
return (*this)[ii];
}
template <typename T, class... SRanges>
T& MutableArrayBase<T,SRanges...>::operator[](const std::tuple<IPTR<typename SRanges::IndexType>...>& is)
{
IndexType ii(*MAB::mProtoI,this->data());
ii(is);
return (*this)[ii];
}
template <typename T, class... SRanges>
typename MutableArrayBase<T,SRanges...>::IndexType MutableArrayBase<T,SRanges...>::begin()
{
IndexType i(*MAB::mProtoI,this->data(),true);
i = 0;
return i.setData(data());
}
template <typename T, class... SRanges>
typename MutableArrayBase<T,SRanges...>::IndexType MutableArrayBase<T,SRanges...>::end()
{
IndexType i(*MAB::mProtoI,this->data(),true);
i = i.max();
return i.setData(data());
}
template <typename T, class... SRanges>
bool MutableArrayBase<T,SRanges...>::isConst() const
{
return false;
}
template <typename T, class... SRanges>
OperationRoot<T,SRanges...>
MutableArrayBase<T,SRanges...>::operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds)
{
return OperationRoot<T,SRanges...>(*this, inds...);
}
template <typename T, class... SRanges>
OperationRoot<T,SRanges...>
MutableArrayBase<T,SRanges...>::op(const std::shared_ptr<CIndexType>& ind)
{
return OperationRoot<T,SRanges...>(data(), *ind);
}
template <typename T, class... SRanges>
ConstOperationRoot<T,SRanges...>
MutableArrayBase<T,SRanges...>::operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const
{
return ConstOperationRoot<T,SRanges...>(*this, inds...);
}
template <typename T, class... SRanges>
ConstOperationRoot<T,SRanges...>
MutableArrayBase<T,SRanges...>::op(const std::shared_ptr<CIndexType>& ind) const
{
return ConstOperationRoot<T,SRanges...>(data(), *ind);
}
template <typename T, class... SRanges>
template <class... MappedRanges>
OperationRoot<T,MappedRanges...>
MutableArrayBase<T,SRanges...>::m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds)
{
static_assert(sizeof...(SRanges) == sizeof...(MappedRanges),
"number of mapped ranges must be equal to number of original ranges");
return OperationRoot<T,MappedRanges...>(*this, inds...);
}
template <typename T, class... SRanges>
template <class... MappedRanges>
ConstOperationRoot<T,MappedRanges...>
MutableArrayBase<T,SRanges...>::m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds) const
{
static_assert(sizeof...(SRanges) == sizeof...(MappedRanges),
"number of mapped ranges must be equal to number of original ranges");
return ConstOperationRoot<T,MappedRanges...>(*this, inds...);
}
} // end namespace CNORXZ

View file

@ -1,187 +0,0 @@
#ifndef __cxz_array_base_h__
#define __cxz_array_base_h__
#include <cstdlib>
#include <vector>
#include <memory>
#include <algorithm>
#include "base_def.h"
#include "mbase_def.h"
#include "ranges/rheader.h"
namespace CNORXZ
{
template <class IndexType>
using IPTR = std::shared_ptr<IndexType>;
template <class IndexType1, class IndexType2>
inline auto operator|(const IPTR<IndexType1>& i1, const IPTR<IndexType2>& i2)
-> decltype(std::make_tuple(i1,i2))
{
return std::make_tuple(i1,i2);
}
template <class IndexType1, class... IndexTypes2>
inline auto operator|(const IPTR<IndexType1>& i1,
const std::tuple<IPTR<IndexTypes2>...>& i2)
-> decltype(std::tuple_cat(std::make_tuple(i1),i2))
{
return std::tuple_cat(std::make_tuple(i1),i2);
}
template <class IndexType2, class... IndexTypes1>
inline auto operator|(const std::tuple<IPTR<IndexTypes1>...>& i1,
const IPTR<IndexType2>& i2)
-> decltype(std::tuple_cat(i1,std::make_tuple(i2)))
{
return std::tuple_cat(i1,std::make_tuple(i2));
}
template <class IndexType>
inline auto operator~(const IPTR<IndexType>& i)
-> decltype(std::make_tuple(i))
{
return std::make_tuple(i);
}
// Explicitely specify subranges in template argument !!!
template <typename T, class... SRanges>
class ArrayBase
{
public:
typedef T value_type;
typedef ContainerRange<SRanges...> CRange;
typedef ConstContainerIndex<T,typename SRanges::IndexType...> CIndexType;
typedef ContainerIndex<T,typename SRanges::IndexType...> IndexType;
protected:
bool mInit = false;
std::shared_ptr<CRange> mRange;
std::shared_ptr<CIndexType> mProtoI;
public:
//DEFAULT_MEMBERS(ArrayBase);
ArrayBase(const std::shared_ptr<SRanges>&... ranges);
ArrayBase(const typename CRange::Space& space);
ArrayBase() = default;
ArrayBase(const ArrayBase& in);
ArrayBase(ArrayBase&& in);
ArrayBase& operator=(const ArrayBase& in);
ArrayBase& operator=(ArrayBase&& in);
virtual ~ArrayBase() = default;
template <typename X>
const T& operator[](const ConstContainerIndex<X,typename SRanges::IndexType...>& i);
const T& operator[](const std::tuple<IPTR<typename SRanges::IndexType>...>& is) const;
virtual const T& operator[](const CIndexType& i) const = 0;
virtual const T& at(const typename CRange::IndexType::MetaType& meta) const = 0;
virtual const T* data() const = 0;
virtual size_t size() const;
virtual bool isSlice() const = 0;
virtual CIndexType begin() const;
virtual CIndexType end() const;
virtual CIndexType cbegin() const;
virtual CIndexType cend() const;
virtual const std::shared_ptr<CRange>& range() const;
virtual bool isConst() const;
virtual std::shared_ptr<ArrayBase<T,AnonymousRange> > anonymous(bool slice = false) const = 0;
virtual ConstOperationRoot<T,SRanges...>
op(const std::shared_ptr<CIndexType>& ind) const;
virtual ConstOperationRoot<T,SRanges...>
operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const;
template <class... MappedRanges>
ConstOperationRoot<T,MappedRanges...>
m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds) const;
virtual bool isInit() const;
template <size_t N>
auto getRangePtr() const
-> decltype(mRange->template getPtr<N>());
};
template <typename T, class... SRanges>
class MutableArrayBase : public ArrayBase<T,SRanges...>
{
public:
typedef ContainerRange<SRanges...> CRange;
typedef ArrayBase<T,SRanges...> MAB;
typedef ContainerIndex<T,typename SRanges::IndexType...> IndexType;
typedef ConstContainerIndex<T,typename SRanges::IndexType...> CIndexType;
using ArrayBase<T,SRanges...>::operator[];
using ArrayBase<T,SRanges...>::at;
using ArrayBase<T,SRanges...>::data;
using ArrayBase<T,SRanges...>::begin;
using ArrayBase<T,SRanges...>::end;
using ArrayBase<T,SRanges...>::cbegin;
using ArrayBase<T,SRanges...>::cend;
DEFAULT_MEMBERS(MutableArrayBase);
MutableArrayBase(const std::shared_ptr<SRanges>&... ranges);
MutableArrayBase(const typename CRange::Space& space);
template <typename X>
T& operator[](const ConstContainerIndex<X,typename SRanges::IndexType...>& i);
T& operator[](const std::tuple<IPTR<typename SRanges::IndexType>...>& is);
virtual T& operator[](const CIndexType& i) = 0;
virtual T& at(const typename CRange::IndexType::MetaType& meta) = 0;
virtual T* data() = 0;
virtual IndexType begin();
virtual IndexType end();
virtual bool isConst() const override;
virtual ConstOperationRoot<T,SRanges...>
op(const std::shared_ptr<CIndexType>& ind) const override;
virtual ConstOperationRoot<T,SRanges...>
operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const override;
virtual OperationRoot<T,SRanges...>
op(const std::shared_ptr<CIndexType>& ind);
virtual OperationRoot<T,SRanges...> operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds);
template <class... MappedRanges>
OperationRoot<T,MappedRanges...>
m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds);
template <class... MappedRanges>
ConstOperationRoot<T,MappedRanges...>
m(const std::shared_ptr<typename MappedRanges::IndexType>&... inds) const;
};
} // end namespace CNORXZ
/* ========================= *
* --- TEMPLATE CODE --- *
* ========================= */
#endif

View file

@ -1,15 +0,0 @@
#include <iostream>
#include <sstream>
#define MA_ERRTAG __FILE__ << '@' << __LINE__ << '(' << __func__ << "): error"
#define MA_WARNTAG __FILE__ << '@' << __LINE__ << ": warning"
#define MA_ERROR(errmsg) {\
std::stringstream ss;\
ss << MA_ERRTAG << ": " << errmsg << std::flush;\
throw std::runtime_error(ss.str()); }
#define MA_WARNING(errmsg) {\
std::cerr << MA_WARNTAG << ": " << errmsg << std::endl; }
#define MA_ASSERT(statement, errmsg) if(not (statement)) { MA_ERROR(errmsg); }

File diff suppressed because it is too large Load diff

View file

@ -1,715 +0,0 @@
// -*- C++ -*-
#ifndef __cxz_operation_h__
#define __cxz_operation_h__
#include <cstdlib>
#include <tuple>
#include <cmath>
#include <map>
#include <utility>
#include <type_traits>
#include "base_def.h"
#include "mbase_def.h"
#include "ranges/rheader.h"
#include "arith.h"
#include "xfor/xfor.h"
#include "type_operations.h"
#include "op_expressions.h"
#include "access.h"
#include "statics/static_for.h"
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
template <typename T, class OperationClass>
class OperationBase
{
public:
OperationClass& THIS() { return static_cast<OperationClass&>(*this); }
const OperationClass& THIS() const { return static_cast<OperationClass const&>(*this); }
template <typename U, class Second>
auto operator+(const OperationBase<U,Second>& in) const;
template <typename U, class Second>
auto operator-(const OperationBase<U,Second>& in) const;
template <typename U, class Second>
auto operator*(const OperationBase<U,Second>& in) const;
template <typename U, class Second>
auto operator/(const OperationBase<U,Second>& in) const;
template <class IndexType>
auto c(const std::shared_ptr<IndexType>& ind) const;
template <class... Indices>
auto sl(const std::shared_ptr<Indices>&... inds) const;
template <class... Indices>
auto p(const std::shared_ptr<Indices>&... inds) const;
template <class... Indices>
auto to(const std::shared_ptr<Indices>&... inds) const;
template <class... Indices>
auto addto(const std::shared_ptr<Indices>&... inds) const;
template <class... Indices>
auto pto(const std::shared_ptr<Indices>&... inds) const;
template <class... Indices>
auto paddto(const std::shared_ptr<Indices>&... inds) const;
template <typename R, class... Args> // Args = Operation Classes
auto a(const std::shared_ptr<function<R,T,typename Args::value_type...>>& ll, const Args&... args) const;
auto ptr() const;
private:
friend OperationClass;
friend OperationTemplate<T,OperationClass>;
OperationBase() = default;
};
template <typename T, class OperationClass>
class OperationTemplate : public OperationBase<T,OperationClass>
{
/* empty per default; specialize if needed */
private:
OperationTemplate() = default;
friend OperationClass;
};
template <typename T>
struct SelfIdentity
{
static inline T& sapply(T& a, T b)
{
return a = b;
}
};
template <class... Ops>
struct OperationTuple
{
OperationTuple(const Ops&... ops) : mOps(ops...) {}
std::tuple<Ops...> mOps;
auto rootSteps(std::intptr_t iPtrNum) const;
};
template <class... Ops>
auto OperationTuple<Ops...>::rootSteps(std::intptr_t iPtrNum) const
{
return sfor_p<0,sizeof...(Ops)>
( [&](auto i){ return std::get<i>(mOps).rootSteps(iPtrNum); },
[&](auto f, auto next) { return f.extend(next); } );
}
template <typename T, class... Ops>
class MOp
{
private:
MOp() = default;
OperationTuple<Ops...> mOps;
public:
static constexpr size_t LAYER = 0;
static constexpr size_t NHLAYER = 0;
static constexpr size_t SIZE = (... + Ops::SIZE);
typedef decltype(mOps.rootSteps(0)) ExtType;
MOp(const Ops&... exprs);
MOp(const MOp& in) = default;
MOp(MOp&& in) = default;
MOp& operator=(const MOp& in) = default;
MOp& operator=(MOp&& in) = default;
inline size_t get(ExtType last) const;
template <typename V>
inline size_t vget(ExtType last) const { return get(last); }
inline MOp& set(ExtType last);
auto rootSteps(std::intptr_t iPtrNum = 0) const -> ExtType;
template <class Expr>
auto loop(Expr exp) const;
T* data() const { assert(0); return nullptr; }
};
template <class OpClass, class NextExpr>
class GetExpr : public ExpressionBase
{
private:
GetExpr() = default;
OpClass mSec;
NextExpr mNExpr;
public:
static constexpr size_t LAYER = 0;
static constexpr size_t NHLAYER = 0;
static constexpr size_t SIZE = OpClass::SIZE + NextExpr::SIZE;
typedef decltype(mSec.rootSteps(0).extend( mNExpr.rootSteps(0) ) ) ExtType;
GetExpr(const OpClass& sec, const NextExpr& nexpr);
GetExpr(const GetExpr& in) = default;
GetExpr(GetExpr&& in) = default;
GetExpr& operator=(const GetExpr& in) = default;
GetExpr& operator=(GetExpr&& in) = default;
virtual std::shared_ptr<ExpressionBase> deepCopy() const override final
{
return std::make_shared<GetExpr<OpClass,NextExpr>>(*this);
}
inline void operator()(size_t start = 0);
inline void get(ExtType last);
template <typename V>
inline void vget(ExtType last) { get(last); }
inline void operator()(size_t start, ExtType last);
auto rootSteps(std::intptr_t iPtrNum = 0) const -> ExtType;
inline void operator()(size_t mlast, DExt last) override final;
inline DExt dRootSteps(std::intptr_t iPtrNum = 0) const override final;
inline DExt dExtension() const override final;
};
template <class OpClass, class NextExpr>
auto mkGetExpr(const OpClass& op, const NextExpr& nexpr)
{
return GetExpr<OpClass,NextExpr>(op, nexpr);
}
template <typename T, class... Ops>
auto mkMOp(const Ops&... exprs)
{
return MOp<T,Ops...>(exprs...);
}
template <typename T, class... Ranges>
class ConstOperationRoot : public OperationTemplate<T,ConstOperationRoot<T,Ranges...> >
{
public:
typedef T value_type;
typedef OperationBase<T,ConstOperationRoot<T,Ranges...> > OT;
typedef ContainerRange<Ranges...> CRange;
typedef ConstContainerIndex<T,typename Ranges::IndexType...> IndexType;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = true;
static constexpr bool VABLE = true;
ConstOperationRoot(const ArrayBase<T,Ranges...>& ma,
const std::shared_ptr<typename Ranges::IndexType>&... indices);
ConstOperationRoot(std::shared_ptr<ArrayBase<T,Ranges...> > maptr,
const std::shared_ptr<typename Ranges::IndexType>&... indices);
ConstOperationRoot(const T* data, const IndexType& ind);
template <class ET>
inline const T& get(ET pos) const;
template <typename V, class ET>
inline const V& vget(ET pos) const;
template <class ET>
inline ConstOperationRoot& set(ET pos);
MExt<None> rootSteps(std::intptr_t iPtrNum = 0) const; // nullptr for simple usage with decltype
template <class Expr>
Expr loop(Expr exp) const;
const T* data() const;
private:
const T* mDataPtr;
const T* mOrigDataPtr;
IndexType mIndex;
std::shared_ptr<ArrayBase<T,Ranges...> > mMaPtr; // never remove this ptr, otherwise we lose temporary container instances!
};
template <typename T, class Op>
class StaticCast : public OperationTemplate<T,StaticCast<T,Op> >
{
private:
Op mOp;
public:
typedef T value_type;
typedef OperationBase<T,StaticCast<T,Op> > OT;
typedef typename Op::CRange CRange;
typedef typename Op::IndexType IndexType;
static constexpr size_t SIZE = Op::SIZE;
static constexpr bool CONT = false;
static constexpr bool VABLE = false;
StaticCast(const Op& op);
template <class ET>
inline T get(ET pos) const;
template <typename V, class ET>
inline V vget(ET pos) const;
template <class ET>
inline StaticCast& set(ET pos);
auto rootSteps(std::intptr_t iPtrNum = 0) const
-> decltype(mOp.rootSteps(iPtrNum));
template <class Expr>
Expr loop(Expr exp) const;
};
template <typename T, class Op>
StaticCast<T,Op> staticcast(const Op& op)
{
return StaticCast<T,Op>(op);
}
template <class Range>
class MetaOperationRoot : public OperationTemplate<typename Range::MetaType,
MetaOperationRoot<Range> >
{
public:
typedef typename Range::IndexType IndexType;
typedef typename IndexType::MetaType value_type;
typedef OperationBase<value_type,MetaOperationRoot<Range> > OT;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = false;
static constexpr bool VABLE = false;
MetaOperationRoot(const std::shared_ptr<IndexType>& ind);
template <class ET>
inline value_type get(ET pos) const;
template <typename V, class ET>
inline V vget(ET pos) const;
template <class ET>
inline MetaOperationRoot& set(ET pos);
MExt<None> rootSteps(std::intptr_t iPtrNum = 0) const; // nullptr for simple usage with decltype
template <class Expr>
Expr loop(Expr exp) const;
private:
mutable IndexType mWorkIndex;
std::shared_ptr<IndexType> mIndex;
};
template <typename T, class... Ranges>
class OperationRoot : public OperationTemplate<T,OperationRoot<T,Ranges...> >
{
public:
typedef T value_type;
typedef OperationBase<T,OperationRoot<T,Ranges...> > OT;
typedef ContainerRange<Ranges...> CRange;
typedef ConstContainerIndex<T,typename Ranges::IndexType...> IndexType;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = true;
static constexpr bool VABLE = true;
private:
T* mDataPtr;
T* mOrigDataPtr;
PointerAccess<T> mDataAcc;
IndexType mIndex;
public:
OperationRoot(MutableArrayBase<T,Ranges...>& ma,
const std::shared_ptr<typename Ranges::IndexType>&... indices);
OperationRoot(MutableArrayBase<T,Ranges...>& ma,
const std::tuple<std::shared_ptr<typename Ranges::IndexType>...>& indices);
OperationRoot(T* data, const IndexType& ind);
template <class Func, class Access, class OpClass>
auto asx(const OpClass& in) const;
template <class Func, class Access, class OpClass>
auto asxExpr(const OpClass& in) const;
template <class Func, class Access, class OpClass, class Index>
auto asx(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
auto assign(const OpClass& in) const;
template <class OpClass>
auto assignExpr(const OpClass& in) const;
template <class OpClass, class Index>
auto assign(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
auto plus(const OpClass& in) const;
template <class OpClass, class Index>
auto plus(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
OperationRoot& operator=(const OpClass& in);
template <class OpClass>
OperationRoot& operator+=(const OpClass& in);
OperationRoot& operator=(const OperationRoot& in);
auto par() { return *this; }
template <class ET>
inline T& get(ET pos) const;
template <typename V, class ET>
inline V& vget(ET pos) const;
template <class ET>
inline OperationRoot& set(ET pos);
MExt<None> rootSteps(std::intptr_t iPtrNum = 0) const; // nullptr for simple usage with decltype
template <class Expr>
Expr loop(Expr exp) const;
T* data() const;
template <class... Indices>
auto sl(const std::shared_ptr<Indices>&... inds)
-> Slice<T,typename Indices::RangeType...>;
};
/*
template <typename T, class... Ranges>
class ParallelOperationRoot : public OperationTemplate<T,ParallelOperationRoot<T,Ranges...> >
{
public:
typedef T value_type;
typedef OperationBase<T,ParallelOperationRoot<T,Ranges...> > OT;
typedef ContainerRange<Ranges...> CRange;
typedef ConstContainerIndex<T,typename Ranges::IndexType...> IndexType;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = true;
static constexpr bool VABLE = true;
private:
T* mDataPtr;
T* mOrigDataPtr;
PointerAccess<T> mDataAcc;
IndexType mIndex;
public:
ParallelOperationRoot(MutableArrayBase<T,Ranges...>& ma,
const std::shared_ptr<typename Ranges::IndexType>&... indices);
ParallelOperationRoot(T* data, const IndexType& ind);
template <class Func, class OpClass>
auto asx(const OpClass& in) const;
template <class Func, class OpClass>
auto asxExpr(const OpClass& in) const;
template <class Func, class OpClass, class Index>
auto asx(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
auto assign(const OpClass& in) const;
template <class OpClass>
auto assignExpr(const OpClass& in) const;
template <class OpClass, class Index>
auto assign(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
auto plus(const OpClass& in) const;
template <class OpClass, class Index>
auto plus(const OpClass& in, const std::shared_ptr<Index>& i) const;
template <class OpClass>
ParallelOperationRoot& operator=(const OpClass& in);
template <class OpClass>
ParallelOperationRoot& operator+=(const OpClass& in);
ParallelOperationRoot& operator=(const ParallelOperationRoot& in);
template <class ET>
inline T& get(ET pos) const;
template <typename V, class ET>
inline V& vget(ET pos) const;
template <class ET>
inline ParallelOperationRoot& set(ET pos);
MExt<None> rootSteps(std::intptr_t iPtrNum = 0) const; // nullptr for simple usage with decltype
template <class Expr>
Expr loop(Expr exp) const;
T* data() const;
};
*/
template <typename T>
class OperationValue : public OperationTemplate<T,OperationValue<T> >
{
public:
typedef T value_type;
typedef OperationBase<T,OperationValue<T> > OT;
typedef ContainerRange<NullRange> CRange;
typedef ConstContainerIndex<T,NullIndex> IndexType;
static constexpr size_t SIZE = 0;
static constexpr bool CONT = true;
static constexpr bool VABLE = false;
OperationValue(const T& val);
template <class ET>
inline const T& get(ET pos) const;
template <typename V, class ET>
inline V vget(ET pos) const;
template <class ET>
inline OperationValue& set(ET pos);
None rootSteps(std::intptr_t iPtrNum = 0) const; // nullptr for simple usage with decltype
template <class Expr>
Expr loop(Expr exp) const;
private:
T mVal;
};
template <typename T, class Op>
class OperationPointer : public OperationTemplate<const T*,OperationPointer<T,Op>>
{
public:
typedef T value_type;
typedef OperationTemplate<const T*,OperationPointer<T,Op>> OT;
static constexpr size_t SIZE = Op::SIZE;
static constexpr bool CONT = false;
private:
Op mOp;
public:
OperationPointer(const Op& op) : mOp(op)
{
static_assert(Op::CONT,
"OperationPointer can only be applied to containing operations");
}
template <class ET>
inline const T* get(ET pos) const;
template <class ET>
inline OperationPointer& set(ET pos);
auto rootSteps(std::intptr_t iPtrNum = 0) const // nullptr for simple usage with decltype
-> decltype(mOp.rootSteps(0));
template <class Expr>
auto loop(Expr exp) const
-> decltype(mOp.loop(exp));
T const** data() const { assert(0); return nullptr; }
};
template <typename T, class OpFunction, class... Ops>
class Operation : public OperationTemplate<T,Operation<T,OpFunction,Ops...> >
{
public:
typedef T value_type;
typedef OperationBase<T,Operation<T,OpFunction,Ops...> > OT;
typedef OpFunction F;
static constexpr size_t SIZE = (... + Ops::SIZE);
static constexpr bool FISSTATIC = OpFunction::FISSTATIC;
static constexpr bool CONT = false;
static constexpr bool VABLE =
(... and (Ops::VABLE and std::is_same<T,typename Ops::value_type>::value));
private:
OperationTuple<Ops...> mOps;
std::shared_ptr<OpFunction> mF; // only if non-static
typedef decltype(mOps.rootSteps(0)) ExtType;
public:
Operation(const Ops&... ops);
Operation(std::shared_ptr<OpFunction> ff, const Ops&... ops);
template <class ET>
inline auto get(ET pos) const;
template <typename V, class ET>
inline auto vget(ET pos) const;
template <class ET>
inline Operation& set(ET pos);
auto rootSteps(std::intptr_t iPtrNum = 0) const
-> ExtType; // nullptr for simple usage with decltype
template <class Expr>
auto loop(Expr exp) const;
T* data() const { assert(0); return nullptr; }
};
template <class OpFunction, class... Ops>
auto mkOperation(const std::shared_ptr<OpFunction>& f, const Ops&... ops)
-> Operation<typename OpFunction::value_type,OpFunction,Ops...>
{
if constexpr(OpFunction::FISSTATIC){
return Operation<typename OpFunction::value_type,OpFunction,Ops...>(ops...);
}
else {
return Operation<typename OpFunction::value_type,OpFunction,Ops...>(f,ops...);
}
}
template <typename T, class Op, class IndexType>
class Contraction : public OperationTemplate<T,Contraction<T,Op,IndexType> >
{
public:
typedef T value_type;
typedef OperationBase<T,Contraction<T,Op,IndexType> > OT;
static constexpr size_t SIZE = Op::SIZE;
static constexpr bool CONT = Op::CONT;
static constexpr bool VABLE = Op::VABLE;
private:
Op mOp;
std::shared_ptr<IndexType> mInd;
public:
typedef decltype(mOp.rootSteps(0)) ETuple;
Contraction(const Op& op, std::shared_ptr<IndexType> ind);
template <class ET>
inline auto get(ET pos) const
-> decltype(mOp.template get<ET>(pos));
template <typename V, class ET>
inline auto vget(ET pos) const
-> decltype(mOp.template vget<V,ET>(pos));
template <class ET>
inline Contraction& set(ET pos);
T* data() const { assert(0); return nullptr; }
auto rootSteps(std::intptr_t iPtrNum = 0) const // nullptr for simple usage with decltype
-> decltype(mOp.rootSteps(iPtrNum));
template <class Expr>
auto loop(Expr exp) const
-> decltype(mInd->iforh(1,mOp.loop(exp)));
};
// for SliceArray
/*
template <typename T, class Op>
class HyperOperation : public OperationTemplate<T,HyperOperation<T,Op> >
{
public:
typedef Op value_type;
typedef OperationTemplate<T,HyperOperation<T,Op> > OT;
static constexpr size_t SIZE = Op::SIZE;
static constexpr bool CONT = false;
static constexpr bool VABLE = false;
private:
Op mOp; // proto
public:
//typedef decltype(mOp.rootSteps(0)) ETuple;
template <class ET>
// include ALL indices (external/internal!!!)
inline auto get(ET pos) const
-> decltype(mOp.template get<ET>(pos));
template <typename V, class ET>
inline auto vget(ET pos) const
-> decltype(mOp.template vget<V,ET>(pos));
template <class ET>
inline HyperOperation& set(ET pos);
T* data() const { assert(0); return nullptr; }
auto rootSteps(std::intptr_t iPtrNum = 0) const // nullptr for simple usage with decltype
-> decltype(mOp.rootSteps(iPtrNum));
template <class Expr>
auto loop(Expr exp) const
-> decltype(mInd->iforh(1,mOp.loop(exp)));
};
*/
}
#include "type_operations.h"
#endif

View file

@ -1,198 +0,0 @@
#include "dynamic_operation.h"
#include "helper_tools.h"
namespace CNORXZ
{
template <typename T, class Operation>
T DynamicOperation<T,Operation>::get(const DExtT& pos) const
{
return mOp.get(pos.expl<ET>());
}
template <typename T, class Operation>
DynamicOperationBase<T>& DynamicOperation<T,Operation>::set(const DExtT& pos)
{
mOp.set(pos.expl<ET>());
return *this;
}
template <typename T, class Operation>
DExtT DynamicOperation<T,Operation>::rootSteps(std::intptr_t iPtrNum) const
{
return DExtT(mkDExt(mkExtT(mOp.rootSteps(iPtrNum))),None(0));
}
template <typename T, class Operation>
DynamicExpression DynamicOperation<T,Operation>::loop(const DynamicExpression& exp) const
{
return mOp.loop(exp);
}
template <typename T, class Operation>
const T* DynamicOperation<T,Operation>::data() const
{
return mOp.data();
}
template <typename T, class Operation>
std::shared_ptr<DynamicOperationBase<T>> DynamicOperation<T,Operation>::deepCopy() const
{
return std::make_shared<DynamicOperation<T,Operation>>(*this);
}
template <typename T, class Operation, class... Ranges>
DynamicOuterOp<T,Operation,Ranges...>::DynamicOuterOp(const DynamicOuterOp& in) :
mThreadId(omp_get_thread_num()), mOp(in.mOp),
mIndices(in.mIndices),
mMa((mThreadId != in.mThreadId) ? std::make_shared<Array<T,Ranges...>>(*in.mMa) : in.mMa),
mProto((mThreadId != in.mThreadId) ? OperationRoot<T,Ranges...>(*mMa,mIndices) : in.mProto),
mL((mThreadId != in.mThreadId) ?
mkILoop(std::make_tuple(*mProto.mOp,mOp), mIndices,
std::make_tuple(mMa),
std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(mIndices) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0})) :
in.mL)
{*mMa = 0;}
template <typename T, class Operation, class... Ranges>
DynamicOuterOp<T,Operation,Ranges...>::DynamicOuterOp(DynamicOuterOp&& in) :
mThreadId(omp_get_thread_num()), mOp(in.mOp),
mIndices(in.mIndices),
mMa((mThreadId != in.mThreadId) ? std::make_shared<Array<T,Ranges...>>(*in.mMa) : in.mMa),
mProto((mThreadId != in.mThreadId) ? OperationRoot<T,Ranges...>(*mMa,mIndices) : in.mProto),
mL((mThreadId != in.mThreadId) ?
mkILoop(std::make_tuple(*mProto.mOp,mOp), mIndices,
std::make_tuple(mMa),
std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(mIndices) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0})) :
in.mL)
{*mMa = 0;}
template <typename T, class Operation, class... Ranges>
DynamicOuterOp<T,Operation,Ranges...>&
DynamicOuterOp<T,Operation,Ranges...>::operator=(const DynamicOuterOp& in)
{
mThreadId = omp_get_thread_num();
mOp = in.mOp;
mIndices = in.mIndices;
if(mThreadId != in.mThreadId){
mMa = std::make_shared<Array<T,Ranges...>>(in.mMa);
mProto = OperationRoot<T,Ranges...>(*mMa,mIndices);
mL = mkILoop(std::make_tuple(*mProto.mOp,mOp), mIndices,
std::make_tuple(mMa),
std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(mIndices) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}));
}
else {
mMa = in.mMa;
mProto = in.mProto;
mL = in.mL;
}
*mMa = 0;
return *this;
}
template <typename T, class Operation, class... Ranges>
DynamicOuterOp<T,Operation,Ranges...>&
DynamicOuterOp<T,Operation,Ranges...>::operator=(DynamicOuterOp&& in)
{
mThreadId = omp_get_thread_num();
mOp = in.mOp;
mIndices = in.mIndices;
if(mThreadId != in.mThreadId){
mMa = std::make_shared<Array<T,Ranges...>>(in.mMa);
mProto = OperationRoot<T,Ranges...>(*mMa,mIndices);
mL = mkILoop(std::make_tuple(*mProto.mOp,mOp), mIndices,
std::make_tuple(mMa),
std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(mIndices) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}));
}
else {
mMa = in.mMa;
mProto = in.mProto;
mL = in.mL;
}
*mMa = 0;
return *this;
}
template <typename T, class Operation, class... Ranges>
DynamicOuterOp<T,Operation,Ranges...>::DynamicOuterOp(const Operation& op,
const std::shared_ptr<typename Ranges::IndexType>&... inds)
: mThreadId(omp_get_thread_num()), mOp(op),
mIndices(inds...),
mMa(std::make_shared<Array<T,Ranges...>>(mkArray<T>(inds->range()...))),
mProto(OperationRoot<T,Ranges...>(*mMa,inds...)),
mL(std::make_tuple(*mProto.mOp,mOp), std::make_tuple(inds...),
std::make_tuple(mMa), std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(inds...) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}))
{}
/*
DynamicOuterOp(const std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<typename Operatrion::value_type,Ranges...>>>>& dyn,
const Operation& op, const std::shared_ptr<Indices>&... inds )
: mThreadId(omp_get_thread_num()),
//mDyn(dyn),
mOp(op), mIndices(inds...),
mMa(std::make_shared<Array<T,Ranges...>>(mkArray<T>(inds->range()...))),
mProto(OperationRoot<T,Ranges...>(*mMa,inds...)),
mL(std::make_tuple(*mProto.mOp,mOp), std::make_tuple(inds...),
std::make_tuple(mMa), std::make_tuple(mProto.mOp->assign( mOp, mkMIndex(inds...) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}))
{}
*/
template <typename T, class Operation, class... Ranges>
OpH<OperationRoot<T,Ranges...>> DynamicOuterOp<T,Operation,Ranges...>::get(const DExtT& pos) const
{
//if(mPrev) mPrev.get(pos.expl<ET>());
mL(0,pos.expl<ET>());
return mProto; // empty
}
template <typename T, class Operation, class... Ranges>
DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>&
DynamicOuterOp<T,Operation,Ranges...>::set(const DExtT& pos)
{
mOp.set(pos.expl<ET>());
return *this;
}
template <typename T, class Operation, class... Ranges>
DExtT DynamicOuterOp<T,Operation,Ranges...>::rootSteps(std::intptr_t iPtrNum) const
{
return DExtT(mkDExt(mkExtT(mL.rootSteps(iPtrNum))),None(0));
}
template <typename T, class Operation, class... Ranges>
DynamicExpression DynamicOuterOp<T,Operation,Ranges...>::loop(const DynamicExpression& exp) const
{
return mOp.loop(exp); // ???!!
}
template <typename T, class Operation, class... Ranges>
const OpH<OperationRoot<T,Ranges...>>* DynamicOuterOp<T,Operation,Ranges...>::data() const
{
return &mProto;
}
/*
template <class Op1, class Op2>
template <class ET>
inline T TwoOp<Op1,Op2>::get(const ET& pos) const
{
return mOp2.get(pos);
}
*/
template <typename T, class Operation, class... Ranges>
std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>>
DynamicOuterOp<T,Operation,Ranges...>::deepCopy() const
{
return std::make_shared<DynamicOuterOp<T,Operation,Ranges...>>(*this);
}
} // namespace CNORXZ

View file

@ -1,209 +0,0 @@
#ifndef __cxz_dynamic_operation_h__
#define __cxz_dynamic_operation_h__
#include "base_def.h"
#include "cxz_operation.h"
namespace CNORXZ
{
template <typename T>
class DynamicOperationBase : public OperationTemplate<T,DynamicOperationBase<T>>
{
public:
typedef T value_type;
typedef OperationBase<T,DynamicOperationBase<T>> OT;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = true;
static constexpr bool VABLE = false;
DynamicOperationBase() = default;
DynamicOperationBase(const DynamicOperationBase& in) = default;
DynamicOperationBase(DynamicOperationBase&& in) = default;
DynamicOperationBase& operator=(const DynamicOperationBase& in) = default;
DynamicOperationBase& operator=(DynamicOperationBase&& in) = default;
virtual T get(const DExtT& pos) const = 0;
virtual DynamicOperationBase& set(const DExtT& pos) = 0;
virtual DExtT rootSteps(std::intptr_t iPtrNum = 0) const = 0;
virtual DynamicExpression loop(const DynamicExpression& exp) const = 0;
virtual const T* data() const = 0;
virtual std::shared_ptr<DynamicOperationBase<T>> deepCopy() const = 0;
};
template <typename T, class Operation>
class DynamicOperation : public DynamicOperationBase<T>
{
private:
Operation mOp;
public:
typedef decltype(mOp.rootSteps()) ET;
//typedef decltype(std::declval<Operation>().rootSteps()) ET;
DynamicOperation() = default;
DynamicOperation(const DynamicOperation& in) = default;
DynamicOperation(DynamicOperation&& in) = default;
DynamicOperation& operator=(const DynamicOperation& in) = default;
DynamicOperation& operator=(DynamicOperation&& in) = default;
DynamicOperation(const Operation& op) : mOp(op) {}
virtual T get(const DExtT& pos) const override final;
virtual DynamicOperationBase<T>& set(const DExtT& pos) override final;
virtual DExtT rootSteps(std::intptr_t iPtrNum = 0) const override final;
virtual DynamicExpression loop(const DynamicExpression& exp) const override final;
virtual const T* data() const override final;
virtual std::shared_ptr<DynamicOperationBase<T>> deepCopy() const override final;
};
template <class Op>
struct OpH
{
std::shared_ptr<Op> mOp;
OpH(const Op& op) : mOp(std::make_shared<Op>(op)) {}
// overload all operations here ...
};
template <typename T, class Operation, class... Ranges>
class DynamicOuterOp : public DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>
{
private:
size_t mThreadId;
//std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>> mDyn;
Operation mOp;
//OperationRoot<T,Ranges...> mProto;
std::tuple<std::shared_ptr<typename Ranges::IndexType>...> mIndices;
std::shared_ptr<Array<T,Ranges...>> mMa;
OpH<OperationRoot<T,Ranges...>> mProto;
typedef ILoop<std::tuple<OperationRoot<T,Ranges...>,Operation>,
std::tuple<std::shared_ptr<typename Ranges::IndexType>...>,
std::tuple<std::shared_ptr<Array<T,Ranges...>>>,
std::tuple<decltype(mProto.mOp->assign( mOp, mkMIndex(std::shared_ptr<typename Ranges::IndexType>()...) ))>> LoopT;
mutable LoopT mL;
public:
typedef decltype(mL.rootSteps()) ET;
//typedef decltype(std::declval<Operation>().rootSteps()) ET;
DynamicOuterOp() : mThreadId(omp_get_thread_num()) {}
DynamicOuterOp(const DynamicOuterOp& in);
DynamicOuterOp(DynamicOuterOp&& in);
DynamicOuterOp& operator=(const DynamicOuterOp& in);
DynamicOuterOp& operator=(DynamicOuterOp&& in);
DynamicOuterOp(const Operation& op, const std::shared_ptr<typename Ranges::IndexType>&... inds);
/*
DynamicOuterOp(const std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<typename Operatrion::value_type,Ranges...>>>>& dyn,
const Operation& op, const std::shared_ptr<Indices>&... inds );
*/
virtual OpH<OperationRoot<T,Ranges...>> get(const DExtT& pos) const override final;
virtual DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>& set(const DExtT& pos) override final;
virtual DExtT rootSteps(std::intptr_t iPtrNum = 0) const override final;
virtual DynamicExpression loop(const DynamicExpression& exp) const override final;
virtual const OpH<OperationRoot<T,Ranges...>>* data() const override final;
virtual std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<T,Ranges...>>>> deepCopy() const override final;
};
template <typename T>
class DynamicO : public OperationTemplate<T,DynamicO<T>>
{
private:
// NOT THREAD SAFE!!!
std::shared_ptr<DynamicOperationBase<T>> mOp;
public:
typedef T value_type;
typedef OperationBase<T,DynamicO<T>> OT;
static constexpr size_t SIZE = 1;
static constexpr bool CONT = true;
static constexpr bool VABLE = false;
DynamicO() = default;
DynamicO(const DynamicO& in) : mOp(in.mOp ? in.mOp->deepCopy() : nullptr) {}
DynamicO(DynamicO&& in) : mOp(in.mOp ? in.mOp->deepCopy() : nullptr) {}
DynamicO& operator=(const DynamicO& in)
{ mOp = in.mOp ? in.mOp->deepCopy() : nullptr; return *this; }
DynamicO& operator=(DynamicO&& in)
{ mOp = in.mOp ? in.mOp->deepCopy() : nullptr; return *this; }
bool init() const { return mOp != nullptr; }
template <class Op>
DynamicO(const Op& op) : mOp(std::make_shared<DynamicOperation<T,Op>>(op)) {}
DynamicO(const std::shared_ptr<DynamicOperationBase<T>>& op) :
mOp(op) {}
template <class X>
inline T get(const DExtTX<X>& pos) const { return mOp->get(pos.reduce()); }
template <typename V,class X>
inline auto vget(const DExtTX<X>& pos) const
{ return mOp->template vget<V>(pos.reduce()); }
template <class X>
inline DynamicO& set(const DExtTX<X>& pos) { mOp->set(pos.reduce()); return *this; }
inline DExtT rootSteps(std::intptr_t iPtrNum = 0) const { return mOp->rootSteps(iPtrNum); }
inline DynamicExpression loop(const DynamicExpression& exp) const { return mOp->loop(exp); }
inline const T* data() const { return mOp->data(); }
};
/*
template <class Op1>
class TwoOp : public OperationTemplate<typename Op2::value_type,TwoOp<Op1>>
{
private:
Op1 mOp1;
typename Op1::value_type mOp2; // mOp1.data()->mOp
public:
typedef typename Op2::value_type value_type;
typedef value_type T;
TwoOp(const Op1& op1);
template <class ET>
inline T get(const ET& pos) const;
};
*/
template <class Operation, class... Indices>
auto mkDynOutOp(const Operation& op, const std::shared_ptr<Indices>&... inds)
{
return DynamicO<OpH<OperationRoot<typename Operation::value_type,
typename Indices::RangeType...>>>
(DynamicOuterOp<typename Operation::value_type,Operation,
typename Indices::RangeType...>(op, inds...));
}
/*
template <class Operation, class... Indices>
auto mkDynOutOp(const std::shared_ptr<DynamicOperationBase<OpH<OperationRoot<typename Operatrion::value_type,Ranges...>>>>& dyn,
const Operation& op, const std::shared_ptr<Indices>&... inds)
{
return DynamicO<OpH<OperationRoot<typename Operation::value_type,
typename Indices::RangeType...>>>
(DynamicOuterOp<typename Operation::value_type,Operation,
typename Indices::RangeType...>(dyn, op, inds...));
}
*/
// Build plan
/*
template <class Operation>
class OperationBuilder
{
};
*/
} // namespace CNORXZ
#endif

View file

@ -1,6 +0,0 @@
#ifdef regFunc1
regFunc1(exp)
#endif

View file

@ -1,99 +0,0 @@
#include "functional_array.h"
namespace CNORXZ
{
/****************************
* FunctionalArray *
****************************/
template <typename T, class Function, class... SRanges>
FunctionalArray<T,Function,SRanges...>::FunctionalArray(const std::shared_ptr<SRanges>&... ranges,
const std::shared_ptr<Function>& func) :
ArrayBase<T,SRanges...>(ranges...), mFunc(func) {}
template <typename T, class Function, class... SRanges>
FunctionalArray<T,Function,SRanges...>::FunctionalArray(const std::shared_ptr<SRanges>&... ranges) :
ArrayBase<T,SRanges...>(ranges...) {}
template <typename T, class Function, class... SRanges>
FunctionalArray<T,Function,SRanges...>::FunctionalArray(const typename CRange::Space& space) :
ArrayBase<T,SRanges...>(space) {}
template <typename T, class Function, class... SRanges>
FunctionalArray<T,Function,SRanges...>::FunctionalArray(const typename CRange::Space& space,
const std::shared_ptr<Function>& func) :
ArrayBase<T,SRanges...>(space), mFunc(func) {}
template <typename T, class Function, class... SRanges>
const T& FunctionalArray<T,Function,SRanges...>::operator[](const IndexType& i) const
{
if constexpr(Function::FISSTATIC){
mVal = Function::apply(i.meta());
}
else {
mVal = (*mFunc)(i.meta());
}
return mVal;
}
template <typename T, class Function, class... SRanges>
const T& FunctionalArray<T,Function,SRanges...>::at(const typename CRange::IndexType::MetaType& meta) const
{
if constexpr(Function::FISSTATIC){
mVal = Function::apply(meta);
}
else {
mVal = (*mFunc)(meta);
}
return mVal;
}
template <typename T, class Function, class... SRanges>
const T* FunctionalArray<T,Function,SRanges...>::data() const
{
return &mVal;
}
template <typename T, class Function, class... SRanges>
bool FunctionalArray<T,Function,SRanges...>::isConst() const
{
return true;
}
template <typename T, class Function, class... SRanges>
bool FunctionalArray<T,Function,SRanges...>::isSlice() const
{
return false;
}
template <typename T, class Function, class... SRanges>
std::shared_ptr<ArrayBase<T,AnonymousRange> > FunctionalArray<T,Function,SRanges...>::anonymous(bool slice) const
{
assert(0); // think about it carefully
return nullptr;
}
template <typename T, class Function, class... SRanges>
ConstOperationRoot<T,SRanges...> FunctionalArray<T,Function,SRanges...>::
operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const
{
if(not mMaPtr){
mMaPtr = std::make_shared<MAType>( MAB::mRange->space() );
(*mMaPtr)(inds...) = exec(inds...);
}
return ConstOperationRoot<T,SRanges...>( *mMaPtr, inds... );
}
template <typename T, class Function, class... SRanges>
auto FunctionalArray<T,Function,SRanges...>::
exec(const std::shared_ptr<typename SRanges::IndexType>&... inds) const
-> Operation<T,Function,MetaOperationRoot<SRanges>...>
{
return mkOperation( mFunc, MetaOperationRoot<SRanges>( inds ) ... );
}
} // namespace CNORXZ

View file

@ -1,61 +0,0 @@
#ifndef __cxz_functional_array__
#define __cxz_functional_array__
#include "cxz_array_base.h"
#include "slice.h"
namespace CNORXZ
{
template <typename T, class Function, class... SRanges>
class FunctionalArray : public ArrayBase<T,SRanges...>
{
public:
typedef ContainerRange<SRanges...> CRange;
typedef ArrayBase<T,SRanges...> MAB;
typedef ConstContainerIndex<T,typename SRanges::IndexType...> IndexType;
typedef Array<T,SRanges...> MAType;
typedef T value_type;
private:
mutable T mVal;
std::shared_ptr<Function> mFunc;
mutable std::shared_ptr<MAType> mMaPtr;
public:
DEFAULT_MEMBERS(FunctionalArray);
FunctionalArray(const std::shared_ptr<SRanges>&... ranges, const std::shared_ptr<Function>& func);
FunctionalArray(const std::shared_ptr<SRanges>&... ranges);
FunctionalArray(const typename CRange::Space& space);
FunctionalArray(const typename CRange::Space& space, const std::shared_ptr<Function>& func);
virtual const T& operator[](const IndexType& i) const override;
virtual const T& at(const typename CRange::IndexType::MetaType& meta) const override;
virtual const T* data() const override;
virtual bool isConst() const override;
virtual bool isSlice() const override;
virtual std::shared_ptr<ArrayBase<T,AnonymousRange> > anonymous(bool slice = false) const override;
auto exec(const std::shared_ptr<typename SRanges::IndexType>&... inds) const
-> Operation<T,Function,MetaOperationRoot<SRanges>...>;
virtual ConstOperationRoot<T,SRanges...>
operator()(const std::shared_ptr<typename SRanges::IndexType>&... inds) const override;
};
} // namespace CNORXZ
/* ========================= *
* --- TEMPLATE CODE --- *
* ========================= */
#endif

View file

@ -1,398 +0,0 @@
#include "helper_tools.h"
namespace CNORXZ
{
template <typename... T>
std::ostream& operator<<(std::ostream& out, const std::tuple<T...>& tp)
{
sfor_pn<0,sizeof...(T)-1>( [&](auto i){ out << std::get<i>(tp) << ", "; return 0; } );
out << std::get<sizeof...(T)-1>(tp);
return out;
}
template <class RangeType>
auto getIndex(std::shared_ptr<RangeType> range)
-> std::shared_ptr<typename RangeType::IndexType>
{
return std::make_shared<typename RangeType::IndexType>(range);
}
template <class RangeType>
auto getIndex()
-> std::shared_ptr<typename RangeType::IndexType>
{
static_assert( RangeType::defaultable, "Range not defaultable" );
static auto f = RangeType::factory();
static auto r = std::dynamic_pointer_cast<RangeType>( f.create() );
return std::make_shared<typename RangeType::IndexType>(r);
}
template <class... RangeTypes>
auto mkMulti(std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<MultiRange<RangeTypes...> >
{
MultiRangeFactory<RangeTypes...> mrf( ranges... );
return std::dynamic_pointer_cast<MultiRange<RangeTypes...> >( mrf.create() );
}
namespace
{
template <size_t N>
struct IndexToRangeTuple
{
template <class... IndexTypes>
static inline void set(std::tuple<std::shared_ptr<typename IndexTypes::RangeType>...>& out,
const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
{
std::get<N>(out) = std::get<N>(indices)->range();
IndexToRangeTuple<N-1>::set(out,indices);
}
};
template <>
struct IndexToRangeTuple<0>
{
template <class... IndexTypes>
static inline void set(std::tuple<std::shared_ptr<typename IndexTypes::RangeType>...>& out,
const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
{
std::get<0>(out) = std::get<0>(indices)->range();
}
};
}
template <class... IndexTypes>
auto indexToRangeTuple(const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
-> std::tuple<std::shared_ptr<typename IndexTypes::RangeType>...>
{
std::tuple<std::shared_ptr<typename IndexTypes::RangeType>...> out;
IndexToRangeTuple<sizeof...(IndexTypes)-1>::set(out, indices);
return out;
}
template <class... IndexTypes>
auto mkMIndex(std::shared_ptr<IndexTypes>... indices)
-> decltype( getIndex( mkMulti( indices->range()... ) ) )
{
auto mi = getIndex( mkMulti( indices->range()... ) );
(*mi)( indices... );
return mi;
}
template <class... IndexTypes>
auto mkMIndex(const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
-> decltype( getIndex( mkMulti( indexToRangeTuple(indices) ) ) )
{
auto mi = getIndex( mkMulti( indexToRangeTuple(indices) ) );
(*mi)( indices );
return mi;
}
template <class Index>
auto mkIndexW(const std::shared_ptr<Index>& ind)
-> std::shared_ptr<IndexW>
{
return std::make_shared<IndexWrapper<Index>>(ind);
}
template <SpaceType STYPE, class Op, class MA, class... RangeTypes>
auto mkGenMapR(const std::tuple<Op,MA>& f, std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<GenMapRange<MapORType<Op,STYPE>,Op,STYPE,RangeTypes...> >
{
GenMapRangeFactory<MapORType<Op,STYPE>,Op,STYPE,RangeTypes...> mrf(f, ranges... );
return createExplicit( mrf );
}
template <SpaceType STYPE, class ORType, class Op, class MA, class... RangeTypes>
auto mkGenMapRwith(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& f,
std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<GenMapRange<ORType,Op,STYPE,RangeTypes...> >
{
GenMapRangeFactory<ORType,Op,STYPE,RangeTypes...> mrf(outr, f, ranges... );
return createExplicit( mrf );
}
template <SpaceType STYPE, class Op, class MA, class... IndexTypes>
auto mkGenMapI(const std::tuple<Op,MA>& f, std::shared_ptr<IndexTypes>... indices)
-> decltype( getIndex( mkGenMapR<STYPE>( f, indices->range()... ) ) )
{
auto mi = getIndex( mkGenMapR<STYPE>( f, indices->range()... ) );
(*mi)(indices...);
return mi;
}
template <class Op, class MA, class... RangeTypes>
auto mkMapR(const std::tuple<Op,MA>& f, std::shared_ptr<RangeTypes>... ranges)
-> decltype( mkGenMapR<SpaceType::ANY>(f, ranges... ) )
{
return mkGenMapR<SpaceType::ANY>(f, ranges... );
}
template <class ORType, class Op, class MA, class... RangeTypes>
auto mkMapRwith(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& f,
std::shared_ptr<RangeTypes>... ranges)
-> decltype( mkGenMapRwith<SpaceType::ANY>(outr, f, ranges... ) )
{
return mkGenMapRwith<SpaceType::ANY>(outr, f, ranges... );
}
template <class Func, class... Indices>
auto mkMapR(const std::shared_ptr<Func>& func, const std::shared_ptr<Indices>&... is)
-> decltype( mkMapR( mkMapOp( func, is... ), is->range()... ) )
{
return mkMapR( mkMapOp( func, is... ), is->range()... );
}
template <class ORType, class Func, class... Indices>
auto mkMapRwith(const std::shared_ptr<ORType>& outr, const std::shared_ptr<Func>& func, const std::shared_ptr<Indices>&... is)
-> decltype( mkMapRwith(outr, mkMapOp( func, is... ), is->range()... ) )
{
return mkMapRwith(outr, mkMapOp( func, is... ), is->range()... );
}
template <class Op, class MA, class... IndexTypes>
auto mkMapI(const std::tuple<Op,MA>& f, std::shared_ptr<IndexTypes>... indices)
-> decltype( mkGenMapI<SpaceType::ANY>(f, indices... ) )
{
return mkGenMapI<SpaceType::ANY>(f, indices... );
}
template <class... RangeTypes>
auto mkMulti(std::tuple<std::shared_ptr<RangeTypes>...> rangesTuple)
-> std::shared_ptr<MultiRange<RangeTypes...>>
{
MultiRangeFactory<RangeTypes...> mrf( rangesTuple );
return std::dynamic_pointer_cast<MultiRange<RangeTypes...> >( mrf.create() );
}
template <class RangeFactory>
auto createExplicit(RangeFactory& rf)
-> std::shared_ptr<typename RangeFactory::oType>
{
return std::dynamic_pointer_cast<typename RangeFactory::oType>( rf.create() );
}
template <class RangeFactory>
auto createExplicit(std::shared_ptr<RangeFactory> rfp)
-> std::shared_ptr<typename RangeFactory::oType>
{
return std::dynamic_pointer_cast<typename RangeFactory::oType>( rfp->create() );
}
template <class Range>
auto createRange(const vector<char>& cvec)
-> std::shared_ptr<Range>
{
const char* dp = cvec.data();
auto ff = createRangeFactory(&dp);
auto rbptr = ff->create();
assert(rbptr->spaceType() == Range::STYPE);
// CATCH CAST ERROR HERE !!!
return std::dynamic_pointer_cast<Range>( rbptr );
}
inline auto createRange(const vector<char>* cvec, int metaType, size_t size)
-> std::shared_ptr<RangeBase>
{
auto f = createSingleRangeFactory(cvec, metaType, size);
return f->create();
}
inline auto createRangeA(const vector<char>* cvec, int metaType, size_t size)
-> std::shared_ptr<AnonymousRange>
{
AnonymousRangeFactory arf(createRange(cvec, metaType, size));
return createExplicit(arf);
}
inline auto cvecMetaCast(const std::shared_ptr<SingleRange<vector<char>,SpaceType::ANY>>& r, int metaType)
-> std::shared_ptr<RangeBase>
{
return createRange(&r->get(0), metaType, r->size());
}
inline auto cvecMetaCastA(const std::shared_ptr<SingleRange<vector<char>,SpaceType::ANY>>& r, int metaType)
-> std::shared_ptr<AnonymousRange>
{
return createRangeA(&r->get(0), metaType, r->size());
}
template <class Range, typename... Args>
auto createRangeE(Args&&... args)
-> std::shared_ptr<Range>
{
typename Range::FType f(args...);
return createExplicit(f);
}
template <size_t N, class MArray>
auto rptr(const MArray& ma)
-> decltype(ma.template getRangePtr<N>())
{
return ma.template getRangePtr<N>();
}
template <class MArray>
auto dynamic(const MArray& ma, bool slice)
-> std::shared_ptr<ArrayBase<typename MArray::value_type,DynamicRange>>
{
DynamicRangeFactory drf(ma.range()->space());
if(slice){
return std::make_shared<ConstSlice<typename MArray::value_type,DynamicRange>>
( std::dynamic_pointer_cast<DynamicRange>( drf.create() ),
ma.data() );
}
else {
return std::make_shared<Array<typename MArray::value_type,DynamicRange>>
( std::dynamic_pointer_cast<DynamicRange>( drf.create() ),
ma.vdata() );
}
}
template <class MArray>
auto mdynamic(MArray& ma, bool slice)
-> std::shared_ptr<MutableArrayBase<typename MArray::value_type,DynamicRange>>
{
DynamicRangeFactory drf(ma.range()->space());
if(slice){
return std::make_shared<Slice<typename MArray::value_type,DynamicRange>>
( std::dynamic_pointer_cast<DynamicRange>( drf.create() ),
ma.data() );
}
else {
return std::make_shared<Array<typename MArray::value_type,DynamicRange>>
( std::dynamic_pointer_cast<DynamicRange>( drf.create() ),
ma.vdata() );
}
}
namespace
{
template <size_t N>
struct CopyRanges
{
template <class Space1, class Space2>
static inline void exec(const Space1& space1, Space2& space2)
{
std::get<N>(space2) = std::get<N>(space1);
CopyRanges<N-1>::exec(space1,space2);
}
};
template <>
struct CopyRanges<0>
{
template <class Space1, class Space2>
static inline void exec(const Space1& space1, Space2& space2)
{
std::get<0>(space2) = std::get<0>(space1);
}
};
}
template <typename T, class Range1, class... RangeTypes>
auto anonToDynView(const ArrayBase<T,Range1,RangeTypes...,AnonymousRange>& ma)
-> ConstSlice<T,Range1,RangeTypes...,DynamicRange>
{
constexpr size_t LAST = sizeof...(RangeTypes)+1;
DynamicRangeFactory drf(rptr<LAST>(ma)->orig());
std::tuple<std::shared_ptr<Range1>,std::shared_ptr<RangeTypes>...,
std::shared_ptr<DynamicRange>> mNSpace;
CopyRanges<LAST-1>::exec(ma.range()->space(),mNSpace);
std::get<LAST>(mNSpace) = createExplicit( drf );
return ConstSlice<T,Range1,RangeTypes...,DynamicRange>(mNSpace, ma.data());
}
template <typename T, class Range1, class... RangeTypes>
auto anonToDynView(MutableArrayBase<T,Range1,RangeTypes...,AnonymousRange>& ma)
-> Slice<T,Range1,RangeTypes...,DynamicRange>
{
constexpr size_t LAST = sizeof...(RangeTypes)+1;
DynamicRangeFactory drf(rptr<LAST>(ma)->orig());
std::tuple<std::shared_ptr<Range1>,std::shared_ptr<RangeTypes>...,
std::shared_ptr<DynamicRange>> mNSpace;
CopyRanges<LAST-1>::exec(ma.range()->space(),mNSpace);
std::get<LAST>(mNSpace) = createExplicit( drf );
return Slice<T,Range1,RangeTypes...,DynamicRange>(mNSpace, ma.data());
}
template <typename T, class Range1, class... RangeTypes>
auto dynToAnonMove(Array<T,Range1,RangeTypes...,DynamicRange>&& ma)
-> Array<T,Range1,RangeTypes...,AnonymousRange>
{
constexpr size_t LAST = sizeof...(RangeTypes)+1;
AnonymousRangeFactory arf(rptr<LAST>(ma)->orig());
std::tuple<std::shared_ptr<Range1>,std::shared_ptr<RangeTypes>...,
std::shared_ptr<AnonymousRange>> mNSpace;
CopyRanges<LAST-1>::exec(ma.range()->space(),mNSpace);
std::get<LAST>(mNSpace) = createExplicit( arf );
return ma.format(mNSpace);
}
template <typename T>
auto anonToDynView(const ArrayBase<T,AnonymousRange>& ma)
-> ConstSlice<T,DynamicRange>
{
DynamicRangeFactory drf(rptr<0>(ma)->orig());
auto mNSpace = std::make_tuple( createExplicit( drf ) );
return ConstSlice<T,DynamicRange>(mNSpace, ma.data());
}
template <typename T>
auto anonToDynView(MutableArrayBase<T,AnonymousRange>& ma)
-> Slice<T,DynamicRange>
{
DynamicRangeFactory drf(rptr<0>(ma)->orig());
auto mNSpace = std::make_tuple( createExplicit( drf ) );
return Slice<T,DynamicRange>(mNSpace, ma.data());
}
template <typename T>
auto dynToAnonMove(Array<T,DynamicRange>&& ma)
-> Array<T,AnonymousRange>
{
AnonymousRangeFactory arf(rptr<0>(ma)->orig());
auto mNSpace = std::make_tuple( createExplicit( arf ) );
return ma.format(mNSpace);
}
template <class Range>
auto metaSlice(const std::shared_ptr<Range>& r)
-> ConstSlice<typename Range::MetaType,ClassicRange>
{
ClassicRF crf(r->size());
return ConstSlice<typename Range::MetaType,ClassicRange>( createExplicit(crf), &r->get(0) );
}
template <class Range, class ORange>
auto metaSlice(const std::shared_ptr<Range>& r, const std::shared_ptr<ORange>& ro)
-> ConstSlice<typename Range::MetaType,ORange>
{
return ConstSlice<typename Range::MetaType,ORange>( ro, &r->get(0) );
}
template <typename T, class... Ranges>
auto mkArray(const std::shared_ptr<Ranges>&... rs)
-> Array<T,Ranges...>
{
return Array<T,Ranges...>(rs...);
}
template <typename T, class... Ranges>
auto mkArray(const std::shared_ptr<Ranges>&... rs, const T& val)
-> Array<T,Ranges...>
{
return Array<T,Ranges...>(rs..., val);
}
template <typename T, class... Ranges>
auto mkArrayPtr(const std::shared_ptr<Ranges>&... rs)
-> std::shared_ptr<Array<T,Ranges...>>
{
return std::make_shared<Array<T,Ranges...>>(rs...);
}
}

View file

@ -1,238 +0,0 @@
#ifndef __cxz_helper_tools_h__
#define __cxz_helper_tools_h__
#include "base_def.h"
#include "slice.h"
#include <ostream>
#include "map_range.h"
#include <functional>
#include "xfor/iloop.h"
namespace CNORXZ
{
template <typename... T>
std::ostream& operator<<(std::ostream& out, const std::tuple<T...>& tp);
template <class RangeType>
auto getIndex(std::shared_ptr<RangeType> range)
-> std::shared_ptr<typename RangeType::IndexType>;
// only if 'RangeType' is defaultable and unique (Singleton)
template <class RangeType>
auto getIndex() -> std::shared_ptr<typename RangeType::IndexType>;
template <class... RangeTypes>
auto mkMulti(std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<MultiRange<RangeTypes...> >;
template <class Op, SpaceType XSTYPE>
using MapORType = SingleRange<typename Op::value_type,XSTYPE>;
template <SpaceType STYPE, class Op, class MA, class... RangeTypes>
auto mkGenMapR(const std::tuple<Op,MA>& f, std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<GenMapRange<MapORType<Op,STYPE>,Op,STYPE,RangeTypes...> >;
template <SpaceType STYPE, class ORType, class Op, class MA, class... RangeTypes>
auto mkGenMapRwith(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& f,
std::shared_ptr<RangeTypes>... ranges)
-> std::shared_ptr<GenMapRange<ORType,Op,STYPE,RangeTypes...> >;
template <SpaceType STYPE, class Op, class MA, class... IndexTypes>
auto mkGenMapI(const std::tuple<Op,MA>& f, std::shared_ptr<IndexTypes>... indices)
-> decltype( getIndex( mkGenMapR<STYPE>( f, indices->range()... ) ) );
template <class Op, class MA, class... RangeTypes>
auto mkMapR(const std::tuple<Op,MA>& f, std::shared_ptr<RangeTypes>... ranges)
-> decltype( mkGenMapR<SpaceType::ANY>(f, ranges... ) );
template <class ORType, class Op, class MA, class... RangeTypes>
auto mkMapRwith(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& f, std::shared_ptr<RangeTypes>... ranges)
-> decltype( mkGenMapRwith<SpaceType::ANY>(outr, f, ranges... ) );
template <class Func, class... Indices>
auto mkMapR(const std::shared_ptr<Func>& func, const std::shared_ptr<Indices>&... is)
-> decltype( mkMapR( mkMapOp( func, is... ), is->range()... ) );
template <class ORType, class Func, class... Indices>
auto mkMapRwith(const std::shared_ptr<ORType>& outr, const std::shared_ptr<Func>& func, const std::shared_ptr<Indices>&... is)
-> decltype( mkMapRwith(outr, mkMapOp( func, is... ), is->range()... ) );
template <class Op, class MA, class... IndexTypes>
auto mkMapI(const std::tuple<Op,MA>& f, std::shared_ptr<IndexTypes>... indices)
-> decltype( mkGenMapI<SpaceType::ANY>(f, indices... ) );
template <class... IndexTypes>
auto indexToRangeTuple(const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
-> std::tuple<std::shared_ptr<typename IndexTypes::RangeType>...>;
template <class... RangeTypes>
auto mkMulti(std::tuple<std::shared_ptr<RangeTypes>...> rangesTuple)
-> std::shared_ptr<MultiRange<RangeTypes...>>;
template <class... IndexTypes>
auto mkMIndex(std::shared_ptr<IndexTypes>... indices)
-> decltype( getIndex( mkMulti( indices.range()... ) ) );
template <class... IndexTypes>
auto mkMIndex(const std::tuple<std::shared_ptr<IndexTypes>...>& indices)
-> decltype( getIndex( mkMulti( indexToRangeTuple(indices) ) ) );
template <class Index>
auto mkIndexW(const std::shared_ptr<Index>& ind)
-> std::shared_ptr<IndexW>;
template <class RangeFactory>
auto createExplicit(RangeFactory& rf)
-> std::shared_ptr<typename RangeFactory::oType>;
template <class RangeFactory>
auto createExplicit(std::shared_ptr<RangeFactory> rfp)
-> std::shared_ptr<typename RangeFactory::oType>;
template <class Range>
auto createRange(const vector<char>& cvec)
-> std::shared_ptr<Range>;
inline auto createRange(const vector<char>* cvec, int metaType, size_t size)
-> std::shared_ptr<RangeBase>;
inline auto createRangeA(const vector<char>* cvec, int metaType, size_t size)
-> std::shared_ptr<AnonymousRange>;
template <class Range, typename... Args>
auto createRangeE(Args&&... args)
-> std::shared_ptr<Range>;
template <size_t N, class MArray>
auto rptr(const MArray& ma)
-> decltype(ma.template getRangePtr<N>());
template <size_t I, class MIndex>
auto get(const std::shared_ptr<MIndex>& i)
-> decltype(i->template getPtr<I>())
{
return i->template getPtr<I>();
}
template <class MArray>
auto dynamic(const MArray& ma, bool slice = false)
-> std::shared_ptr<ArrayBase<typename MArray::value_type,DynamicRange>>;
template <class MArray>
auto mdynamic(MArray& ma, bool slice)
-> std::shared_ptr<MutableArrayBase<typename MArray::value_type,DynamicRange>>;
template <typename T, class Range1, class... RangeTypes>
auto anonToDynView(const ArrayBase<T,Range1,RangeTypes...,AnonymousRange>& ma)
-> ConstSlice<T,Range1,RangeTypes...,DynamicRange>;
template <typename T, class Range1, class... RangeTypes>
auto anonToDynView(MutableArrayBase<T,Range1,RangeTypes...,AnonymousRange>& ma)
-> Slice<T,Range1,RangeTypes...,DynamicRange>;
template <typename T, class Range1, class... RangeTypes>
auto dynToAnonMove(Array<T,Range1,RangeTypes...,DynamicRange>&& ma)
-> Array<T,Range1,RangeTypes...,AnonymousRange>;
template <typename T>
auto anonToDynView(const ArrayBase<T,AnonymousRange>& ma)
-> ConstSlice<T,DynamicRange>;
template <typename T>
auto anonToDynView(MutableArrayBase<T,AnonymousRange>& ma)
-> Slice<T,DynamicRange>;
template <typename T>
auto dynToAnonMove(Array<T,DynamicRange>&& ma)
-> Array<T,AnonymousRange>;
template <class Range>
auto metaSlice(const std::shared_ptr<Range>& r)
-> ConstSlice<typename Range::MetaType,ClassicRange>;
template <class Range, class ORange>
auto metaSlice(const std::shared_ptr<Range>& r, const std::shared_ptr<ORange>& ro)
-> ConstSlice<typename Range::MetaType,ORange>;
template <typename T, class... Ranges>
auto mkArray(const std::shared_ptr<Ranges>&... rs)
-> Array<T,Ranges...>;
template <typename T, class... Ranges>
auto mkArrayPtr(const std::shared_ptr<Ranges>&... rs)
-> std::shared_ptr<Array<T,Ranges...>>;
template <typename T, class... Ranges>
auto mkArray(const std::shared_ptr<Ranges>&... rs, const T& val)
-> Array<T,Ranges...>;
template <class OpTp, class IndTp, class VarTp, class LTp>
auto mkILoop(const OpTp& opTp, const IndTp& indTp, const VarTp& varTp, const LTp& lTp,
const std::array<size_t,std::tuple_size<LTp>::value>& umpos,
const std::array<size_t,std::tuple_size<VarTp>::value>& setzero)
-> CNORXZInternal::ILoop<OpTp,IndTp,VarTp,LTp>
{
return CNORXZInternal::ILoop<OpTp,IndTp,VarTp,LTp>(opTp, indTp, varTp, lTp, umpos, setzero);
}
template <class CF>
auto mkPILoop(const CF& cf)
-> CNORXZInternal::PILoop<CF>
{
return CNORXZInternal::PILoop<CF>(cf);
}
template <class IndexType>
inline void For(const std::shared_ptr<IndexType>& ind, const std::function<void(void)>& ll)
{
for((*ind) = 0; ind->pos() != ind->max(); ++(*ind)){
ll();
}
}
// parallel:
template <class IndexType>
inline void PFor(const std::shared_ptr<IndexType>& ind,
const std::function<void(const std::shared_ptr<IndexType>&)>& ll)
{
const int max = static_cast<int>(ind->max());
int i = 0;
#pragma omp parallel shared(ind,ll) private(i)
{
#pragma omp for nowait
for(i = 0; i < max; i++) {
auto ii = getIndex( ind->range() );
((*ii) = i)();
ll(ii);
}
}
}
template <class Index>
inline auto mkOp(const std::shared_ptr<Index>& i)
-> decltype(std::declval<FunctionalArray<typename Index::MetaType,
identity<typename Index::MetaType>,typename Index::RangeType> >
().exec(i))
{
FunctionalArray<typename Index::MetaType,
identity<typename Index::MetaType>,
typename Index::RangeType> fma(i->range());
return fma.exec(i);
}
template <typename R, typename... Ts>
struct Func
{
static inline std::shared_ptr<function<R,Ts...>> mk(const std::function<R(Ts...)>& ll)
{
return std::make_shared<function<R,Ts...>>(ll);
}
};
}
#endif

View file

@ -1,448 +0,0 @@
#include "high_level_operation.h"
namespace CNORXZ
{
template <typename T, class Op>
DynamicO<T> mkDynOp1(const Op& op)
{
return DynamicO<T>(op);
}
template <class ROP>
template <class... Indices>
template <class Op, class... Ops>
void HighLevelOpBase<ROP>::RetT<Indices...>::appendOuterM(const Op& op, const Ops&... ops)
{
// does not check anything regarding input !!!
if(outer.init()){
outer = mkDynOp1<size_t>(mkMOp<size_t>(outer,op,ops...));
}
else {
outer = mkDynOp1<size_t>(mkMOp<size_t>(op,ops...));
}
}
template <class ROP>
template <class... Indices>
void HighLevelOpBase<ROP>::RetT<Indices...>::appendOuterM()
{}
template <class ROP>
template <class... Indices>
void HighLevelOpBase<ROP>::RetT<Indices...>::appendOuter(const DynamicO<size_t>& in)
{
if(in.init()){
if(outer.init()){
outer = mkDynOp1<size_t>(mkMOp<size_t>(outer,in));
}
else {
outer = in;
}
}
}
template <class ROP>
template <class... Indices>
void HighLevelOpBase<ROP>::RetT<Indices...>::appendOuter(const RetT& in)
{
appendOuter(in.outer);
}
template <class ROP>
HighLevelOpRoot<ROP>::HighLevelOpRoot(const ROP& op) : mOp(op) {}
template <class ROP>
bool HighLevelOpRoot<ROP>::root() const
{
return true;
}
template <class ROP>
template <class... Inds>
auto HighLevelOpRoot<ROP>::xcreate(const std::shared_ptr<Inds>&... inds)
-> typename B::template RetT<Inds...>
{
assert(0);
return typename B::template RetT<Inds...>();
}
template <class ROP>
ROP* HighLevelOpRoot<ROP>::get()
{
return &mOp;
}
template <class ROP>
auto HighLevelOpRoot<ROP>::vget()
-> VOP*
{
return nullptr;
}
template <class ROP>
HighLevelOpValue<ROP>::HighLevelOpValue(const VOP& op) : mOp(op) {}
template <class ROP>
bool HighLevelOpValue<ROP>::root() const
{
return true;
}
template <class ROP>
template <class... Inds>
auto HighLevelOpValue<ROP>::xcreate(const std::shared_ptr<Inds>&... inds)
-> typename B::template RetT<Inds...>
{
assert(0);
return typename B::template RetT<Inds...>();
}
template <class ROP>
ROP* HighLevelOpValue<ROP>::get()
{
return nullptr;
}
template <class ROP>
auto HighLevelOpValue<ROP>::vget()
-> VOP*
{
return &mOp;
}
namespace
{
template <size_t N, class... Indices>
struct Create
{
template <class ROP, class OpF, class... OPs>
struct ccx
{
template <size_t M, class... DOPs>
static inline void
cccx(typename HighLevelOpBase<ROP>::template RetT<Indices...>& res,
const std::array<std::shared_ptr<HighLevelOpBase<ROP>>,M>& in,
const std::shared_ptr<Indices>&... inds,
const OPs&... ops,
const DOPs&... dops)
{
//static_assert(N > 0, "N > 0 failed");
auto& inn = std::get<N>(in);
if(not inn->root()){
auto dop = inn->create(inds...);
auto op = *dop.op.data()->mOp;
res.appendOuter(dop);
assert(dop.op.init());
if constexpr(N > 0){
typedef decltype(op) OP;
Create<N-1,Indices...>::template ccx<ROP,OpF,OP,OPs...>::template cccx<M>
(res, in, inds..., op, ops..., dop, dops...);
}
else {
res.op = mkDynOutOp(mkFOp<OpF>(op,ops...), inds...);
res.appendOuterM(dop.op,dops.op...);
}
}
else {
auto op = inn->get();
auto vop = inn->vget();
if constexpr(N > 0){
typedef typename std::remove_reference<decltype(*op)>::type OP;
typedef typename std::remove_reference<decltype(*vop)>::type VOP;
if(op != nullptr){
Create<N-1,Indices...>::template ccx<ROP,OpF,OP,OPs...>::template cccx<M>
(res, in, inds..., *op, ops..., dops...);
}
else {
Create<N-1,Indices...>::template ccx<ROP,OpF,VOP,OPs...>::template cccx<M>
(res, in, inds..., *vop, ops..., dops...);
}
}
else {
if(op != nullptr){
res.op = mkDynOutOp(mkFOp<OpF>(*op,ops...), inds...);
}
else {
res.op = mkDynOutOp(mkFOp<OpF>(*vop,ops...), inds...);
}
res.appendOuterM(dops.op...);
}
}
}
};
};
}
template <class ROP, class OpF, size_t N>
HighLevelOp<ROP,OpF,N>::HighLevelOp(std::array<std::shared_ptr<HighLevelOpBase<ROP>>,N> in) : mIn(in) {}
template <class ROP, class OpF, size_t N>
bool HighLevelOp<ROP,OpF,N>::root() const
{
return false;
}
template <class ROP, class OpF, size_t N>
ROP* HighLevelOp<ROP,OpF,N>::get()
{
assert(0);
return nullptr;
}
template <class ROP, class OpF, size_t N>
auto HighLevelOp<ROP,OpF,N>::vget()
-> VOP*
{
assert(0);
return nullptr;
}
template <class ROP, class OpF, size_t N>
template <class... Inds>
auto HighLevelOp<ROP,OpF,N>::xcreate(const std::shared_ptr<Inds>&... inds)
-> typename B::template RetT<Inds...>
{
typename B::template RetT<Inds...> res;
Create<N-1,Inds...>::template ccx<ROP,OpF>::template cccx<N>
(res,mIn,inds...);
return res;
}
template <class ROP>
HighLevelOpHolder<ROP>::HighLevelOpHolder(const std::shared_ptr<HighLevelOpBase<ROP>>& op) : mOp(op) {}
template <class ROP>
bool HighLevelOpHolder<ROP>::root() const
{
return mOp->root();
}
template <class ROP>
template <class... Inds>
auto HighLevelOpHolder<ROP>::create(const std::shared_ptr<Inds>&... inds) const
-> decltype(mOp->create(inds...))
{
return mOp->create(inds...);
}
template <class ROP>
auto HighLevelOpHolder<ROP>::get()
-> decltype(mOp->get())
{
return mOp->get();
}
template <class ROP>
std::shared_ptr<HighLevelOpBase<ROP>> HighLevelOpHolder<ROP>::op() const
{
return mOp;
}
template <class ROP>
HighLevelOpHolder<ROP> HighLevelOpHolder<ROP>::operator*(const HighLevelOpHolder& in) const
{
return HighLevelOpHolder<ROP>
( std::make_shared<HighLevelOp<ROP,multipliesx<double,double>,2>>
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,2>({mOp, in.mOp}) ) );
}
template <class ROP>
HighLevelOpHolder<ROP> HighLevelOpHolder<ROP>::operator+(const HighLevelOpHolder& in) const
{
return HighLevelOpHolder<ROP>
( std::make_shared<HighLevelOp<ROP,plusx<double,double>,2>>
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,2>({mOp, in.mOp}) ) );
}
template <class ROP>
HighLevelOpHolder<ROP> HighLevelOpHolder<ROP>::operator-(const HighLevelOpHolder& in) const
{
return HighLevelOpHolder<ROP>
( std::make_shared<HighLevelOp<ROP,minusx<double,double>,2>>
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,2>({mOp, in.mOp}) ) );
}
template <class ROP>
HighLevelOpHolder<ROP> HighLevelOpHolder<ROP>::operator/(const HighLevelOpHolder& in) const
{
return HighLevelOpHolder<ROP>
( std::make_shared<HighLevelOp<ROP,dividesx<double,double>,2>>
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,2>({mOp, in.mOp}) ) );
}
template <class F, class ROP, class... ROPs>
HighLevelOpHolder<ROP> mkSFunc(const HighLevelOpHolder<ROP>& a, const HighLevelOpHolder<ROPs>&... as)
{
constexpr size_t N = sizeof...(ROPs)+1;
return HighLevelOpHolder<ROP>
( std::make_shared<HighLevelOp<ROP,F,N>>
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,N>({a.op(), as.op()...}) ) );
}
template <class ROP>
template <class... Indices>
HighLevelOpHolder<ROP>& HighLevelOpHolder<ROP>::xassign(const HighLevelOpHolder& in,
const std::shared_ptr<DynamicIndex>& di,
const std::shared_ptr<Indices>&... is)
{
const size_t dim = di->dim();
if(dim > 2){
auto ci1 = di->getP(dim-2)->reduced();
auto ci2 = di->getP(dim-1)->reduced();
assert(ci1 != nullptr);
assert(ci2 != nullptr);
auto odi = mkSubSpaceX(di, dim-2);
auto mi = mkMIndex(is..., odi);
this->assign(in, mi, ci1, ci2);
}
else {
assert(dim == 2 or dim == 1);
auto ci1 = di->getP(dim-1)->reduced();
assert(ci1 != nullptr);
auto odi = mkSubSpaceX(di, dim-1);
auto mi = mkMIndex(is..., odi);
this->assign(in, mi, ci1);
}
return *this;
}
template <class ROP>
template <class... Indices>
HighLevelOpHolder<ROP>& HighLevelOpHolder<ROP>::xplus(const HighLevelOpHolder& in,
const std::shared_ptr<DynamicIndex>& di,
const std::shared_ptr<Indices>&... is)
{
const size_t dim = di->dim();
if(dim > 2){
auto ci1 = di->getP(dim-2)->reduced();
auto ci2 = di->getP(dim-1)->reduced();
assert(ci1 != nullptr);
assert(ci2 != nullptr);
auto odi = mkSubSpaceX(di, dim-2);
auto mi = mkMIndex(is..., odi);
this->plus(in, mi, ci1, ci2);
}
else {
assert(dim == 2 or dim == 1);
auto ci1 = di->getP(dim-1)->reduced();
assert(ci1 != nullptr);
auto odi = mkSubSpaceX(di, dim-1);
auto mi = mkMIndex(is..., odi);
this->plus(in, mi, ci1);
}
return *this;
}
template <class Ind1, class Ind2, class... Inds>
std::string printInd(const std::shared_ptr<Ind1>& ind1, const std::shared_ptr<Ind2>& ind2,
const std::shared_ptr<Inds>&... inds)
{
return std::to_string(reinterpret_cast<std::intptr_t>(ind1.get())) + "(" +
std::to_string(ind1->max()) + "), " + printInd(ind2, inds...);
}
template <class Ind1>
std::string printInd(const std::shared_ptr<Ind1>& ind1)
{
return std::to_string(reinterpret_cast<std::intptr_t>(ind1.get())) + "(" + std::to_string(ind1->max()) + ")";
}
template <class ROP>
template <class MIndex, class... Indices>
HighLevelOpHolder<ROP>& HighLevelOpHolder<ROP>::assign(const HighLevelOpHolder& in,
const std::shared_ptr<MIndex>& mi,
const std::shared_ptr<Indices>&... inds)
{
auto xx = mkArrayPtr<double>(nullr());
ROP& opr = *mOp->get();
if(in.root()){
auto inx = in;
opr.par().assign( *inx.get(), mkMIndex(mi,inds...) )();
return *this;
}
auto loop = mkPILoop
( [&opr,&in,&xx,&inds...,this](){
auto inx = in;
auto dop = inx.create(inds...);
DynamicO<size_t> gexp;
if(dop.outer.init()){
gexp = mkDynOp1<size_t>(mkMOp<size_t>(dop.outer,dop.op));
}
else {
gexp = mkDynOp1<size_t>(mkMOp<size_t>(dop.op));
}
auto xloop = mkILoop(std::make_tuple(*dop.op.data()->mOp),
std::make_tuple(inds...),
std::make_tuple(xx),
std::make_tuple(opr.assign( *dop.op.data()->mOp,
mkMIndex(inds...) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}));
return mkGetExpr(gexp, xloop); });
mi->pifor(1,loop)();
return *this;
}
template <class ROP>
template <class MIndex, class... Indices>
HighLevelOpHolder<ROP>& HighLevelOpHolder<ROP>::plus(const HighLevelOpHolder& in,
const std::shared_ptr<MIndex>& mi,
const std::shared_ptr<Indices>&... inds)
{
auto xx = mkArrayPtr<double>(nullr());
ROP& opr = *mOp->get();
if(in.root()){
auto inx = in;
opr.par().plus( *inx.get(), mkMIndex(mi,inds...) )();
return *this;
}
auto loop = mkPILoop
( [&opr,&in,&xx,&inds...,this](){
auto inx = in;
auto dop = inx.create(inds...);
DynamicO<size_t> gexp;
if(dop.outer.init()){
gexp = mkDynOp1<size_t>(mkMOp<size_t>(dop.outer,dop.op));
}
else {
gexp = mkDynOp1<size_t>(mkMOp<size_t>(dop.op));
}
auto xloop = mkILoop(std::make_tuple(*dop.op.data()->mOp),
std::make_tuple(inds...),
std::make_tuple(xx),
std::make_tuple(opr.plus( *dop.op.data()->mOp,
mkMIndex(inds...) )),
std::array<size_t,1>({1}), std::array<size_t,1>({0}));
return mkGetExpr(gexp, xloop); });
mi->pifor(1,loop)();
return *this;
}
template <class ROP>
HighLevelOpHolder<ROP> mkHLO(const ROP& op)
{
return HighLevelOpHolder<ROP>(std::make_shared<HighLevelOpRoot<ROP>>( op ) );
}
template <class ROP>
HighLevelOpHolder<ROP> mkHLOV(double val)
{
return HighLevelOpHolder<ROP>(std::make_shared<HighLevelOpValue<ROP>>
( OperationValue<double>(val) ) );
}
#define SP " "
#define regFunc1(fff) template <class ROP> \
HighLevelOpHolder<ROP> hl_##fff (const HighLevelOpHolder<ROP>& in) \
{ return HighLevelOpHolder<ROP>( std::make_shared<HighLevelOp<ROP,x_##fff <double>,1>> \
( std::array<std::shared_ptr<HighLevelOpBase<ROP>>,1>( {in.op()} ) ) ); } \
#include "extensions/math.h"
#undef regFunc1
#undef SP
}

View file

@ -1,279 +0,0 @@
#ifndef __cxz_high_level_operation_h__
#define __cxz_high_level_operation_h__
#include "base_def.h"
#include "ranges/rheader.h"
#include "dynamic_operation.h"
namespace CNORXZ
{
typedef ClassicRange CR;
typedef CR::IndexType CI;
typedef std::shared_ptr<CI> CIP;
typedef OperationRoot<double,CR,DynamicRange> OpCD;
typedef OperationRoot<double,DynamicRange> OpD;
extern template class OperationRoot<double,CR,DynamicRange>;
extern template class OperationRoot<double,DynamicRange>;
template <typename T, class Op>
DynamicO<T> mkDynOp1(const Op& op);
std::shared_ptr<DynamicIndex> mkSubSpaceX(const std::shared_ptr<DynamicIndex>& di, size_t max);
template <class ROP>
class HighLevelOpBase
{
public:
typedef OperationValue<double> VOP;
template <class... Indices>
struct RetT
{
DynamicO<OpH<OperationRoot<double,typename Indices::RangeType...>>> op;
DynamicO<size_t> outer;
template <class Op, class... Ops>
void appendOuterM(const Op& op, const Ops&... ops);
void appendOuterM();
void appendOuter(const DynamicO<size_t>& in);
void appendOuter(const RetT& in);
};
virtual bool root() const = 0;
#define reg_ind1(I1) virtual RetT<I1> create \
(const std::shared_ptr<I1>& ind1) = 0
#define reg_ind2(I1,I2) virtual RetT<I1,I2> create \
(const std::shared_ptr<I1>& ind1,const std::shared_ptr<I2>& ind2) = 0
#define reg_ind3(I1,I2,I3) virtual RetT<I1,I2,I3> create \
(const std::shared_ptr<I1>& ind1,const std::shared_ptr<I2>& ind2,const std::shared_ptr<I3>& ind3) = 0
//#include "hl_reg_ind.h"
reg_ind1(ClassicRange::IndexType);
reg_ind2(ClassicRange::IndexType,ClassicRange::IndexType);
reg_ind3(ClassicRange::IndexType,ClassicRange::IndexType,ClassicRange::IndexType);
#undef reg_ind1
#undef reg_ind2
#undef reg_ind3
virtual ROP* get() = 0;
virtual VOP* vget() = 0;
};
template <class ROP>
class HighLevelOpRoot : public HighLevelOpBase<ROP>
{
private:
typedef HighLevelOpBase<ROP> B;
typedef typename B::VOP VOP;
template <class... Inds>
typename B::template RetT<Inds...> xcreate(const std::shared_ptr<Inds>&... inds);
ROP mOp;
public:
HighLevelOpRoot(const ROP& op);
virtual bool root() const override final;
#define reg_ind1(I1) virtual typename B::template RetT<I1> create \
(const std::shared_ptr<I1>& ind1) \
override final { return xcreate(ind1); }
#define reg_ind2(I1,I2) virtual typename B::template RetT<I1,I2> create \
(const std::shared_ptr<I1>& ind1, const std::shared_ptr<I2>& ind2) \
override final { return xcreate(ind1,ind2); }
#define reg_ind3(I1,I2,I3) virtual typename B::template RetT<I1,I2,I3> create \
(const std::shared_ptr<I1>& ind1, const std::shared_ptr<I2>& ind2, const std::shared_ptr<I3>& ind3) \
override final { return xcreate(ind1,ind2,ind3); }
//#include "hl_reg_ind.h"
reg_ind1(ClassicRange::IndexType);
reg_ind2(ClassicRange::IndexType,ClassicRange::IndexType);
reg_ind3(ClassicRange::IndexType,ClassicRange::IndexType,ClassicRange::IndexType);
virtual ROP* get() override final;
virtual VOP* vget() override final;
};
extern template class HighLevelOpBase<OpCD>;
extern template class HighLevelOpBase<OpD>;
extern template class HighLevelOpRoot<OpCD>;
extern template class HighLevelOpRoot<OpD>;
template <class ROP>
class HighLevelOpValue : public HighLevelOpBase<ROP>
{
private:
typedef HighLevelOpBase<ROP> B;
typedef typename B::VOP VOP;
template <class... Inds>
typename B::template RetT<Inds...> xcreate(const std::shared_ptr<Inds>&... inds);
VOP mOp;
public:
HighLevelOpValue(const VOP& vop);
virtual bool root() const override final;
//#include "hl_reg_ind.h"
reg_ind1(ClassicRange::IndexType);
reg_ind2(ClassicRange::IndexType,ClassicRange::IndexType);
reg_ind3(ClassicRange::IndexType,ClassicRange::IndexType,ClassicRange::IndexType);
virtual ROP* get() override final;
virtual VOP* vget() override final;
};
template <class OpF, class... Ops>
auto mkFOp(const Ops&... ops)
{
return Operation<double,OpF,Ops...>(ops...);
}
template <class ROP, class OpF, size_t N>
class HighLevelOp : public HighLevelOpBase<ROP>
{
public:
typedef HighLevelOpBase<ROP> B;
typedef typename B::VOP VOP;
private:
std::array<std::shared_ptr<HighLevelOpBase<ROP>>,N> mIn;
template <class... Inds>
auto xcreate(const std::shared_ptr<Inds>&... inds)
-> typename B::template RetT<Inds...>;
public:
HighLevelOp(std::array<std::shared_ptr<HighLevelOpBase<ROP>>,N> in);
virtual bool root() const override final;
virtual ROP* get() override final;
virtual VOP* vget() override final;
//#include "hl_reg_ind.h"
reg_ind1(ClassicRange::IndexType);
reg_ind2(ClassicRange::IndexType,ClassicRange::IndexType);
reg_ind3(ClassicRange::IndexType,ClassicRange::IndexType,ClassicRange::IndexType);
#undef reg_ind1
#undef reg_ind2
#undef reg_ind3
};
extern template class HighLevelOp<OpCD,plusx<double,double>,2>;
extern template class HighLevelOp<OpCD,minusx<double,double>,2>;
extern template class HighLevelOp<OpCD,multipliesx<double,double>,2>;
extern template class HighLevelOp<OpCD,dividesx<double,double>,2>;
extern template class HighLevelOp<OpD,plusx<double,double>,2>;
extern template class HighLevelOp<OpD,minusx<double,double>,2>;
extern template class HighLevelOp<OpD,multipliesx<double,double>,2>;
extern template class HighLevelOp<OpD,dividesx<double,double>,2>;
#define regFunc1(fff) \
extern template class HighLevelOp<OpCD,x_##fff<double>,1>; \
extern template class HighLevelOp<OpD,x_##fff<double>,1>;
#include "extensions/math.h"
#undef regFunc1
template <class ROP>
class HighLevelOpHolder
{
private:
std::shared_ptr<HighLevelOpBase<ROP>> mOp;
public:
HighLevelOpHolder() = default;
HighLevelOpHolder(const HighLevelOpHolder& in) = default;
HighLevelOpHolder(HighLevelOpHolder&& in) = default;
HighLevelOpHolder& operator=(const HighLevelOpHolder& in) = default;
HighLevelOpHolder& operator=(HighLevelOpHolder&& in) = default;
HighLevelOpHolder(const std::shared_ptr<HighLevelOpBase<ROP>>& op);
bool root() const;
template <class... Inds>
auto create(const std::shared_ptr<Inds>&... inds) const
-> decltype(mOp->create(inds...));
auto get() -> decltype(mOp->get());
std::shared_ptr<HighLevelOpBase<ROP>> op() const;
HighLevelOpHolder operator*(const HighLevelOpHolder& in) const;
HighLevelOpHolder operator+(const HighLevelOpHolder& in) const;
HighLevelOpHolder operator-(const HighLevelOpHolder& in) const;
HighLevelOpHolder operator/(const HighLevelOpHolder& in) const;
template <class... Indices>
HighLevelOpHolder& xassign(const HighLevelOpHolder& in,
const std::shared_ptr<DynamicIndex>& di,
const std::shared_ptr<Indices>&... is);
template <class... Indices>
HighLevelOpHolder& xplus(const HighLevelOpHolder& in,
const std::shared_ptr<DynamicIndex>& di,
const std::shared_ptr<Indices>&... is);
template <class MIndex, class... Indices>
HighLevelOpHolder& assign(const HighLevelOpHolder& in,
const std::shared_ptr<MIndex>& mi,
const std::shared_ptr<Indices>&... inds);
template <class MIndex, class... Indices>
HighLevelOpHolder& plus(const HighLevelOpHolder& in,
const std::shared_ptr<MIndex>& mi,
const std::shared_ptr<Indices>&... inds);
};
extern template class HighLevelOpHolder<OpCD>;
extern template class HighLevelOpHolder<OpD>;
template <class F, class ROP, class... ROPs>
HighLevelOpHolder<ROP> mkSFunc(const HighLevelOpHolder<ROP>& a, const HighLevelOpHolder<ROPs>&... as);
template <class ROP>
HighLevelOpHolder<ROP> mkHLO(const ROP& op);
template <class ROP>
HighLevelOpHolder<ROP> mkHLOV(double val);
extern template HighLevelOpHolder<OpCD> mkHLO(const OpCD& op);
extern template HighLevelOpHolder<OpD> mkHLO(const OpD& op);
extern template HighLevelOpHolder<OpCD> mkHLOV(double val);
extern template HighLevelOpHolder<OpD> mkHLOV(double val);
#define regFunc1(fff) template <class ROP> \
HighLevelOpHolder<ROP> hl_##fff (const HighLevelOpHolder<ROP>& in);
#include "extensions/math.h"
#undef regFunc1
#define regFunc1(fff) template <class ROP> \
HighLevelOpHolder<ROP> hl_##fff (const HighLevelOpHolder<ROP>& in); \
extern template HighLevelOpHolder<OpCD> hl_##fff (const HighLevelOpHolder<OpCD>& in); \
extern template HighLevelOpHolder<OpD> hl_##fff (const HighLevelOpHolder<OpD>& in);
#include "extensions/math.h"
#undef regFunc1
}
#endif

View file

@ -1,3 +0,0 @@
#include "high_level_operation.h"
#include "high_level_operation.cc.h"

View file

@ -1,704 +0,0 @@
#include "map_range.h"
#include <type_traits>
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
/**************
* OpExpr *
**************/
template <class Op, class Index, class Expr, SpaceType STYPE>
OpExpr<Op,Index,Expr,STYPE>::OpExpr(const Op& mapf, const Index* ind,
size_t step, Expr ex) :
mIndPtr(ind), mSPos(mIndPtr->pos()), mMax(mIndPtr->max()),
mStep(step), mExpr( ex ),
mOp(mapf),
//mExt(ex.rootSteps( reinterpret_cast<std::intptr_t>( mIndPtr )))
mExt( mOp.rootSteps( reinterpret_cast<std::intptr_t>( mIndPtr ) ).extend
( ex.rootSteps( reinterpret_cast<std::intptr_t>( mIndPtr ) ) ) )
{
assert(mIndPtr != nullptr);
}
template <class Op, class Index, class Expr, SpaceType STYPE>
std::shared_ptr<ExpressionBase> OpExpr<Op,Index,Expr,STYPE>::deepCopy() const
{
return std::make_shared<OpExpr<Op,Index,Expr,STYPE>>(*this);
}
template <class Op, class Index, class Expr, SpaceType STYPE>
inline void OpExpr<Op,Index,Expr,STYPE>::operator()(size_t mlast, DExt last)
{
operator()(mlast, std::dynamic_pointer_cast<ExtT<ExtType>>(last)->ext());
}
template <class Op, class Index, class Expr, SpaceType STYPE>
inline void OpExpr<Op,Index,Expr,STYPE>::operator()(size_t mlast,
ExtType last)
{
constexpr size_t NEXT = Op::SIZE;
const ExtType nxpos = last;
const size_t pos = mIndPtr->posAt( mOp.get( nxpos ) );
if(pos != mIndPtr->max()){
const ExtType npos = last + mExt*pos;
const size_t mnpos = PosForward<ForType::DEFAULT>::valuex(mlast, mStep, pos);
mExpr(mnpos, getX<NEXT>( npos ) );
}
}
template <class Op, class Index, class Expr, SpaceType STYPE>
inline void OpExpr<Op,Index,Expr,STYPE>::operator()(size_t mlast)
{
const ExtType last;
constexpr size_t NEXT = Op::SIZE;
const ExtType nxpos = last;
const size_t pos = mIndPtr->posAt( mOp.get( nxpos ) );
if(pos != mIndPtr->max()){
const ExtType npos = last + mExt*pos;
const size_t mnpos = PosForward<ForType::DEFAULT>::valuex(mlast, mStep, pos);
mExpr(mnpos, getX<NEXT>( npos ));
}
}
template <class Op, class Index, class Expr, SpaceType STYPE>
auto OpExpr<Op,Index,Expr,STYPE>::rootSteps(std::intptr_t iPtrNum) const
-> ExtType
{
return mOp.rootSteps(iPtrNum).extend( mExpr.rootSteps(iPtrNum) );
//return mExpr.rootSteps(iPtrNum).extend( mOp.rootSteps(iPtrNum) );
}
template <class Op, class Index, class Expr, SpaceType STYPE>
DExt OpExpr<Op,Index,Expr,STYPE>::dRootSteps(std::intptr_t iPtrNum) const
{
return std::make_shared<ExtT<ExtType>>(rootSteps(iPtrNum));
}
template <class Op, class Index, class Expr, SpaceType STYPE>
DExt OpExpr<Op,Index,Expr,STYPE>::dExtension() const
{
return std::make_shared<ExtT<ExtType>>(mExt);
}
/******************
* MapIndex *
******************/
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <class MRange>
GenMapIndex<OIType,Op,XSTYPE,Indices...>::GenMapIndex(const std::shared_ptr<MRange>& range) :
IndexInterface<GenMapIndex<OIType,Op,XSTYPE,Indices...>,typename Op::value_type>(range, 0)
{
std::get<sizeof...(Indices)>(mBlockSizes) = 1;
sfor_mn<sizeof...(Indices),0>
( [&](auto i) {
auto r = range->template getPtr<i>();
std::get<i>(mIPack) = r->beginPtr();
*std::get<i>(mIPack) = 0;
std::get<i>(mBlockSizes) = sfor_p<i,sizeof...(Indices)>
( [&](auto j) { return std::get<j>(mIPack)->max(); } ,
[&](auto a, auto b) { return a * b; });
return 0;
});
IB::mPos = sfor_m<sizeof...(Indices),0>
( [&](auto i) { return std::get<i>(mIPack); },
[&](auto a, auto b) {return a->pos() + b*a->max();}, 0 );
mOutIndex = std::make_shared<OIType>
( std::dynamic_pointer_cast<RangeType>( IB::mRangePtr )->outRange()->begin() );
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <size_t DIR>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::up()
{
static_assert(DIR < sizeof...(Indices), "DIR exceeds number of sub-indices");
IB::mPos += sfor_p<DIR,sizeof...(Indices)>
( [&](auto i) { return std::get<i>(mIPack)->max(); },
[&](auto a, auto b) { return a * b; } );
sfor_m<DIR+1,0>
( [&](auto i) {
auto& si = *std::get<i>( mIPack );
if(si.last() and i != 0) { si = 0; return true; }
else { ++si; return false; }
return false;
} );
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <size_t DIR>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::down()
{
static_assert(DIR < sizeof...(Indices), "DIR exceeds number of sub-indices");
IB::mPos -= sfor_p<DIR,sizeof...(Indices)>
( [&](auto i) { return std::get<i>(mIPack)->max(); },
[&](auto a, auto b) { return a * b; } );
sfor_m<DIR+1,0>
( [&](auto i) {
auto& si = *std::get<i>( mIPack );
if(si.first() and i != 0) { si = si.max()-1; return true; }
else { --si; return false; }
return false;
} );
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <size_t N>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::get() const -> decltype( *std::get<N>( mIPack ) )&
{
return *std::get<N>(mIPack);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <size_t N>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::getPtr() const -> decltype( std::get<N>( mIPack ) )&
{
return std::get<N>(mIPack);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::outIndex() const -> std::shared_ptr<OIType>
{
return mOutIndex;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::operator()(const std::shared_ptr<Indices>&... indices)
{
return (*this)(std::make_tuple(indices...));
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::operator()(const std::tuple<std::shared_ptr<Indices>...>& indices)
{
sfor_pn<0,sizeof...(Indices)>
( [&](auto i) { std::get<i>(mIPack) = std::get<i>(indices); return 0; } );
RangeHelper::setIndexPack<sizeof...(Indices)-1>(mIPack, IB::mPos);
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
IndexType GenMapIndex<OIType,Op,XSTYPE,Indices...>::type() const
{
return IndexType::MULTI;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::operator=(size_t pos)
{
(*mOutIndex) = pos;
IB::mPos = mOutIndex->pos();
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::operator++()
{
++(*mOutIndex);
IB::mPos = mOutIndex->pos();
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::operator--()
{
--(*mOutIndex);
IB::mPos = mOutIndex->pos();
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
int GenMapIndex<OIType,Op,XSTYPE,Indices...>::pp(std::intptr_t idxPtrNum)
{
mOutIndex->pp(idxPtrNum);
IB::mPos = mOutIndex->pos();
return 1;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
int GenMapIndex<OIType,Op,XSTYPE,Indices...>::mm(std::intptr_t idxPtrNum)
{
mOutIndex->mm(idxPtrNum);
IB::mPos = mOutIndex->pos();
return 1;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
std::string GenMapIndex<OIType,Op,XSTYPE,Indices...>::stringMeta() const
{
return std::dynamic_pointer_cast<RangeType>( IB::mRangePtr )->stringMeta(IB::mPos);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
typename GenMapIndex<OIType,Op,XSTYPE,Indices...>::MetaType GenMapIndex<OIType,Op,XSTYPE,Indices...>::meta() const
{
return mOutIndex->meta();
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
GenMapIndex<OIType,Op,XSTYPE,Indices...>& GenMapIndex<OIType,Op,XSTYPE,Indices...>::at(const MetaType& metaPos)
{
mOutIndex->at(metaPos);
IB::mPos = mOutIndex->pos();
return *this;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
size_t GenMapIndex<OIType,Op,XSTYPE,Indices...>::posAt(const MetaType& metaPos) const
{
return range()->outRange()->getMeta(metaPos);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
size_t GenMapIndex<OIType,Op,XSTYPE,Indices...>::dim() const
{
return sizeof...(Indices);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
bool GenMapIndex<OIType,Op,XSTYPE,Indices...>::first() const
{
return IB::mPos == 0;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
bool GenMapIndex<OIType,Op,XSTYPE,Indices...>::last() const
{
return IB::mPos == IB::mMax - 1;
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
std::shared_ptr<typename GenMapIndex<OIType,Op,XSTYPE,Indices...>::RangeType>
GenMapIndex<OIType,Op,XSTYPE,Indices...>::range() const
{
return std::dynamic_pointer_cast<RangeType>( IB::mRangePtr );
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <size_t N>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::getPtr() -> decltype( std::get<N>( mIPack ) )&
{
return std::get<N>(mIPack);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
size_t GenMapIndex<OIType,Op,XSTYPE,Indices...>::getStepSize(size_t n) const
{
if(n >= sizeof...(Indices)){
assert(0);
// throw !!
}
return mBlockSizes[n+1];
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <class Exprs>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::ifor(size_t step, Exprs exs) const
{
return RangeHelper::mkFor<0>
(0, mIPack, mBlockSizes,
OpExpr<Op,GenMapIndex<OIType,Op,XSTYPE,Indices...>,Exprs,XSTYPE>
( range()->map(), this, step, exs ));
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <class Exprs>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::pifor(size_t step, Exprs exs) const
{
return ifor(step, exs);
}
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
template <class Exprs>
auto GenMapIndex<OIType,Op,XSTYPE,Indices...>::iforh(size_t step, Exprs exs) const
{
return ifor(step, exs);
}
/*************************
* MapRangeFactory *
*************************/
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::GenMapRangeFactory(const std::shared_ptr<ORType>& outr,
const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs)
{
mProd = std::shared_ptr< GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( new GenMapRange<ORType,Op,XSTYPE,Ranges...>( outr, mapf, rs... ) );
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::GenMapRangeFactory(const std::shared_ptr<ORType>& outr,
const std::tuple<Op,MA>& mapf,
const typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::Space& st)
{
mProd = std::shared_ptr< GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( new GenMapRange<ORType,Op,XSTYPE,Ranges...>( outr, mapf, st ) );
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::GenMapRangeFactory(const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs)
{
mProd = std::shared_ptr< GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( new GenMapRange<ORType,Op,XSTYPE,Ranges...>( mapf, rs... ) );
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::GenMapRangeFactory(const std::tuple<Op,MA>& mapf,
const typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::Space& st)
{
mProd = std::shared_ptr< GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( new GenMapRange<ORType,Op,XSTYPE,Ranges...>( mapf, st ) );
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
std::shared_ptr<RangeBase> GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::create()
{
mProd = checkIfCreated( std::dynamic_pointer_cast<oType>( mProd )->mSpace );
setSelf();
return mProd;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
std::shared_ptr<RangeBase> GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>::checkIfCreated(const std::tuple<std::shared_ptr<Ranges>...>& ptp)
{
std::shared_ptr<RangeBase> out;
bool check = false;
for(auto& x: MapRangeFactoryProductMap::mAleadyCreated){
if(x.second.size() == sizeof...(Ranges)){
check = sfor_p<0,sizeof...(Ranges)>
( [&](auto i) { return reinterpret_cast<std::intptr_t>( std::get<i>(ptp).get() ) == x.second[i]; },
[&](auto a, auto b) { return a and b; } );
if(check){
out = x.first;
break;
}
}
}
if(not check){
vector<std::intptr_t> pv(sizeof...(Ranges));
sfor_pn<0,sizeof...(Ranges)>
( [&](auto i) { pv[i] = reinterpret_cast<std::intptr_t>( std::get<i>(ptp).get() ); return 0; } );
pv.push_back( reinterpret_cast<std::intptr_t>
( &std::dynamic_pointer_cast<oType>( mProd )->mMapf ) );
MapRangeFactoryProductMap::mAleadyCreated[mProd] = pv;
out = mProd;
}
return out;
}
/******************
* MapRange *
******************/
template <SpaceType XSTYPE>
struct OutRangeMaker
{};
template <>
struct OutRangeMaker<SpaceType::ANY>
{
template <class MapF, class ORType>
static void mk(std::shared_ptr<ORType>& outRange, Array<size_t,ORType>& mapMult, const MapF& mapf)
{
std::map<typename MapF::value_type,size_t> mult;
for(auto ii = mapf.begin(); ii.max() != ii.pos(); ++ii) {
mult[mapf[ii]]++;
}
vector<typename MapF::value_type> outmeta(mult.size());
vector<size_t> outmult(mult.size());
size_t cnt = 0;
for(auto& x: mult){
outmeta[cnt] = x.first;
outmult[cnt] = x.second;
++cnt;
}
typename ORType::FType orf(outmeta);
outRange = std::dynamic_pointer_cast<ORType>( orf.create() );
mapMult = Array<size_t,ORType>( outRange, outmult );
}
};
template <>
struct OutRangeMaker<SpaceType::NONE>
{
template <class MapF, class ORType>
static void mk(std::shared_ptr<ORType>& outRange, Array<size_t,ORType>& mapMult, const MapF& mapf)
{
static_assert( std::is_same<size_t,typename MapF::value_type>::value,
"out range value type for NONE must be size_t" );
size_t max = 0;
for(auto ii = mapf.begin(); ii.max() != ii.pos(); ++ii) {
max = mapf[ii]+1 > max ? mapf[ii]+1 : max;
}
vector<size_t> mult(max,0);
for(auto ii = mapf.begin(); ii.max() != ii.pos(); ++ii) {
mult[mapf[ii]]++;
}
vector<size_t> outmult(mult.size());
size_t cnt = 0;
for(auto& x: mult){
outmult[cnt++] = x;
}
typename ORType::FType orf(max);
outRange = std::dynamic_pointer_cast<ORType>( orf.create() );
mapMult = Array<size_t,ORType>( outRange, outmult );
}
};
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
void GenMapRange<ORType,Op,XSTYPE,Ranges...>::mkOutRange(const MA& mapf)
{
//FunctionalArray<typename MapF::value_type,MapF,Ranges...> fma(mSpace, mMapf);
OutRangeMaker<XSTYPE>::mk(mOutRange,mMapMult,mapf);
auto i = mapf.begin();
mMapPos.resize(i.max());
for(; i.pos() != i.max(); ++i){
mMapPos[i.pos()] = mOutRange->getMeta( mapf[i] );
}
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRange<ORType,Op,XSTYPE,Ranges...>::GenMapRange(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs) :
mSpace(std::make_tuple(rs...)),
mMapf(std::get<0>(mapf)),
mOutRange(outr),
mMapMult(mOutRange,0),
mMapPos(std::get<1>(mapf).size(),mOutRange->size())
{
auto& ma = std::get<1>(mapf);
auto jj = mMapMult.begin();
for(auto ii = ma.begin(); ii.pos() != ii.max(); ++ii){
++mMapMult[jj.at(ma[ii])];
mMapPos[ii.pos()] = jj.pos();
}
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRange<ORType,Op,XSTYPE,Ranges...>::GenMapRange(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const Space& space) :
mSpace(space),
mMapf(std::get<0>(mapf)),
mOutRange(outr),
mMapMult(mOutRange,0),
mMapPos(std::get<1>(mapf).size(),mOutRange->size())
{
auto& ma = std::get<1>(mapf);
auto jj = mMapMult.begin();
for(auto ii = ma.begin(); ii.pos() != ii.max(); ++ii){
++mMapMult[jj.at(ma[ii])];
mMapPos[ii.pos()] = jj.pos();
}
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRange<ORType,Op,XSTYPE,Ranges...>::GenMapRange(const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs) :
mSpace(std::make_tuple(rs...)),
mMapf(std::get<0>(mapf))
{
mkOutRange(std::get<1>(mapf));
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class MA>
GenMapRange<ORType,Op,XSTYPE,Ranges...>::GenMapRange(const std::tuple<Op,MA>& mapf, const Space& space) :
mSpace( space ),
mMapf(std::get<0>(mapf))
{
mkOutRange(std::get<1>(mapf));
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <size_t N>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::get() const -> decltype( *std::get<N>( mSpace ) )&
{
return *std::get<N>(mSpace);
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <size_t N>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::getPtr() const -> decltype( std::get<N>( mSpace ) )&
{
return std::get<N>(mSpace);
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::outRange() const -> std::shared_ptr<ORType>
{
return mOutRange;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
const Op& GenMapRange<ORType,Op,XSTYPE,Ranges...>::map() const
{
return mMapf;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
size_t GenMapRange<ORType,Op,XSTYPE,Ranges...>::dim() const
{
return sdim;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
size_t GenMapRange<ORType,Op,XSTYPE,Ranges...>::size() const
{
return mOutRange->size();
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
SpaceType GenMapRange<ORType,Op,XSTYPE,Ranges...>::spaceType() const
{
return SpaceType::ANY;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
const typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::Space& GenMapRange<ORType,Op,XSTYPE,Ranges...>::space() const
{
return mSpace;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
vector<size_t> GenMapRange<ORType,Op,XSTYPE,Ranges...>::typeNum() const
{
vector<size_t> o;
RangeHelper::getTypeNum<sizeof...(Ranges)-1>(o,mSpace);
return o;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
size_t GenMapRange<ORType,Op,XSTYPE,Ranges...>::cmeta(char* target, size_t pos) const
{
//MetaType* xtarget = reinterpret_cast<MetaType*>(target);
assert(0);
return 0;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
size_t GenMapRange<ORType,Op,XSTYPE,Ranges...>::cmetaSize() const
{
return RangeHelper::getCMetaSize<0>(mSpace);
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
std::string GenMapRange<ORType,Op,XSTYPE,Ranges...>::stringMeta(size_t pos) const
{
auto i = begin();
i = pos;
return "[ " + RangeHelper::getStringMeta<0>(i) + " ]";
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
vector<char> GenMapRange<ORType,Op,XSTYPE,Ranges...>::data() const
{
DataHeader h = dataHeader();
vector<char> out;
//out.reserve(h.metaSize + sizeof(DataHeader));
char* hcp = reinterpret_cast<char*>(&h);
out.insert(out.end(), hcp, hcp + sizeof(DataHeader));
sfor_pn<0,sizeof...(Ranges)>
( [&](auto i) {
vector<char> part = std::get<i>(mSpace)->data();
out.insert(out.end(), part.begin(), part.end());
return 0;
} );
return out;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
DataHeader GenMapRange<ORType,Op,XSTYPE,Ranges...>::dataHeader() const
{
DataHeader h;
h.spaceType = static_cast<int>( SpaceType::ANY );
h.metaSize = sizeof...(Ranges);
h.multiple = 1;
return h;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::IndexType GenMapRange<ORType,Op,XSTYPE,Ranges...>::begin() const
{
GenMapIndex<typename ORType::IndexType,Op,XSTYPE,typename Ranges::IndexType...>
i( std::dynamic_pointer_cast<GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis ) ) );
i = 0;
return i;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::IndexType GenMapRange<ORType,Op,XSTYPE,Ranges...>::end() const
{
GenMapIndex<typename ORType::IndexType,Op,XSTYPE,typename Ranges::IndexType...>
i( std::dynamic_pointer_cast<GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis )) );
i = size();
return i;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::mapMultiplicity() const
-> const Array<size_t,ORType>&
{
return mMapMult;
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::explMapMultiplicity() const
-> ConstSlice<size_t,GenMapRange>
{
/*
auto tmp = mMapMult;
return tmp.format( std::dynamic_pointer_cast<GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis )) );
*/
return mMapMult.slformat(std::dynamic_pointer_cast<GenMapRange<ORType,Op,XSTYPE,Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis )));
}
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
vector<size_t> GenMapRange<ORType,Op,XSTYPE,Ranges...>::mapPos() const
{
return mMapPos;
}
/*
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
template <class... ERanges>
auto GenMapRange<ORType,Op,XSTYPE,Ranges...>::cat(const std::shared_ptr<MapRange<ERanges...> >& erange)
-> std::shared_ptr<GenMapRange<Ranges...,ERanges...> >
{
auto crange = std::tuple_cat(mSpace, erange->space());
MapRangeFactory<Ranges...,ERanges...> rf(crange);
return std::dynamic_pointer_cast<MapRange<Ranges...,ERanges...> >(rf.create());
}
*/
}

View file

@ -1,354 +0,0 @@
// -*- C++ -*-
#ifndef __cxz_map_range_h__
#define __cxz_map_range_h__
#include <cstdlib>
#include <tuple>
#include <memory>
#include <map>
#include "mbase_def.h"
#include "ranges/range_base.h"
#include "ranges/index_base.h"
#include "map_range_factory_product_map.h"
#include "ranges/x_to_string.h"
#include "ranges/type_map.h"
#include "xfor/xfor.h"
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
template <class Func, class... Indices>
auto mkMapOp(const std::shared_ptr<Func>& func,
const std::shared_ptr<Indices>&... is)
-> decltype(std::make_tuple(FunctionalArray<typename Func::value_type,Func,
typename Indices::RangeType...>().exec(is...),
FunctionalArray<typename Func::value_type,Func,
typename Indices::RangeType...>()))
{
typedef FunctionalArray<typename Func::value_type,Func,typename Indices::RangeType...> FMA;
if(Func::FISSTATIC){
FMA fma(is->range()...);
return std::make_tuple(fma.exec(is...),fma);
}
else {
FMA fma(is->range()...,func);
return std::make_tuple(fma.exec(is...),fma);
}
}
template <class Op, class Index, class Expr, SpaceType STYPE = SpaceType::ANY>
//template <class MapF, class IndexPack, class Expr, SpaceType STYPE = SpaceType::ANY>
class OpExpr : public ExpressionBase
{
public:
//typedef typename Index::OIType OIType;
//typedef SingleIndex<typename Op::value_type,STYPE> OIType;
static constexpr size_t LAYER = Expr::LAYER + 1;
static constexpr size_t SIZE = Expr::SIZE + Op::SIZE;
static constexpr size_t NHLAYER = Expr::NHLAYER + 1;
private:
OpExpr() = default;
const Index* mIndPtr;
//const OIType* mIndPtr;
size_t mSPos;
size_t mMax;
size_t mStep;
Expr mExpr;
Op mOp;
typedef decltype(mOp.rootSteps(std::declval<intptr_t>()).extend( mExpr.rootSteps(std::declval<intptr_t>()) )) ExtType;
ExtType mExt;
public:
OpExpr(const OpExpr& in) = default;
OpExpr(OpExpr&& in) = default;
OpExpr& operator=(const OpExpr& in) = default;
OpExpr& operator=(OpExpr&& in) = default;
OpExpr(const Op& mapf, const Index* ind, size_t step, Expr ex);
virtual std::shared_ptr<ExpressionBase> deepCopy() const override final;
template <size_t VS>
inline auto vec() const { return *this; }
inline void operator()(size_t mlast, DExt last) override final;
inline void operator()(size_t mlast, ExtType last);
inline void operator()(size_t mlast = 0) override final;
auto rootSteps(std::intptr_t iPtrNum = 0) const -> ExtType;
virtual DExt dRootSteps(std::intptr_t iPtrNum = 0) const override final;
virtual DExt dExtension() const override final;
};
template <class OIType, class Op, SpaceType XSTYPE, class... Indices>
class GenMapIndex : public IndexInterface<GenMapIndex<OIType,Op,XSTYPE,Indices...>,
typename Op::value_type>
//std::tuple<typename Indices::MetaType...> >
{
public:
typedef IndexInterface<GenMapIndex<OIType,Op,XSTYPE,Indices...>,
typename Op::value_type> IB;
//std::tuple<typename Indices::MetaType...> > IB;
typedef std::tuple<std::shared_ptr<Indices>...> IndexPack;
//typedef std::tuple<typename Indices::MetaType...> MetaType;
typedef typename Op::value_type MetaType;
typedef GenMapRange<typename OIType::RangeType,Op,XSTYPE,typename Indices::RangeType...> RangeType;
typedef GenMapIndex IType;
//typedef SingleIndex<typename Op::value_type,XSTYPE> OIType;
static constexpr IndexType sType() { return IndexType::SINGLE; }
static constexpr size_t sDim() { return sizeof...(Indices); }
static constexpr size_t totalDim() { return (... * Indices::totalDim()); }
static void check_type() { static_assert( std::is_same<typename OIType::MetaType,typename Op::value_type>::value, "inconsitent value types" ); }
static constexpr SpaceType STYPE = XSTYPE;
static constexpr bool PARALLEL = false;
private:
IndexPack mIPack;
std::array<size_t,sizeof...(Indices)+1> mBlockSizes;
std::shared_ptr<OIType> mOutIndex;
public:
const IndexPack& pack() const { return mIPack; }
GenMapIndex() = delete;
// NO DEFAULT HERE !!!
// ( have to assign sub-indices (ptr!) correctly )
//MapIndex(const MapIndex& in);
//MapIndex& operator=(const MapIndex& in);
template <class MRange>
GenMapIndex(const std::shared_ptr<MRange>& range);
template <size_t DIR>
GenMapIndex& up();
template <size_t DIR>
GenMapIndex& down();
template <size_t N>
auto get() const -> decltype( *std::get<N>( mIPack ) )&;
template <size_t N>
auto getPtr() const -> decltype( std::get<N>( mIPack ) )&;
template <size_t N>
size_t getBlockSize() const { return std::get<N>(mBlockSizes); }
std::shared_ptr<OIType> outIndex() const;
// raplace instances (in contrast to its analogon in ConstContainerIndex
// MultiIndices CANNOT be influences be its subindices, so there is
// NO foreign/external controll)
// Do NOT share index instances between two or more MapIndex instances
GenMapIndex& operator()(const std::shared_ptr<Indices>&... indices);
GenMapIndex& operator()(const std::tuple<std::shared_ptr<Indices>...>& indices);
// ==== >>>>> STATIC POLYMORPHISM <<<<< ====
IndexType type() const;
GenMapIndex& operator=(size_t pos);
GenMapIndex& operator++();
GenMapIndex& operator--();
int pp(std::intptr_t idxPtrNum);
int mm(std::intptr_t idxPtrNum);
std::string stringMeta() const;
MetaType meta() const;
GenMapIndex& at(const MetaType& metaPos);
size_t posAt(const MetaType& metaPos) const;
size_t dim() const;
bool first() const;
bool last() const;
std::shared_ptr<RangeType> range() const;
template <size_t N>
auto getPtr() -> decltype( std::get<N>( mIPack ) )&;
size_t getStepSize(size_t n) const;
template <class Exprs>
auto ifor(size_t step, Exprs exs) const; // first step arg not used!
template <class Exprs>
auto pifor(size_t step, Exprs exs) const; // NO MULTITHREADING
template <class Exprs>
auto iforh(size_t step, Exprs exs) const;
};
/*************************
* MapRangeFactory *
*************************/
// NOT THREAD SAVE
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
class GenMapRangeFactory : public RangeFactoryBase
{
public:
//typedef SingleRange<typename Op::value_type,XSTYPE> ORType;
typedef GenMapRange<ORType,Op,XSTYPE,Ranges...> oType;
GenMapRangeFactory() = delete;
template <class MA>
GenMapRangeFactory(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs);
template <class MA>
GenMapRangeFactory(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::Space& st);
template <class MA>
GenMapRangeFactory(const std::tuple<Op,MA>& mapf, const std::shared_ptr<Ranges>&... rs);
template <class MA>
GenMapRangeFactory(const std::tuple<Op,MA>& mapf,
const typename GenMapRange<ORType,Op,XSTYPE,Ranges...>::Space& space);
virtual std::shared_ptr<RangeBase> create() override;
private:
std::shared_ptr<RangeBase> checkIfCreated(const std::tuple<std::shared_ptr<Ranges>...>& ptp);
};
/******************
* MapRange *
******************/
template <class ORType, class Op, SpaceType XSTYPE, class... Ranges>
class GenMapRange : public RangeInterface<GenMapIndex<typename ORType::IndexType,Op,XSTYPE,typename Ranges::IndexType...> >
{
public:
typedef RangeBase RB;
typedef std::tuple<std::shared_ptr<Ranges>...> Space;
typedef GenMapIndex<typename ORType::IndexType,Op,XSTYPE,typename Ranges::IndexType...> IndexType;
typedef typename Op::value_type MetaType;
protected:
GenMapRange() = delete;
GenMapRange(const GenMapRange& in) = delete;
GenMapRange& operator=(const GenMapRange& in) = delete;
template <class MA>
GenMapRange(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const std::shared_ptr<Ranges>&... rs);
template <class MA>
GenMapRange(const std::shared_ptr<ORType>& outr, const std::tuple<Op,MA>& mapf,
const Space& space);
template <class MA>
GenMapRange(const std::tuple<Op,MA>& mapf, const Space& space);
template <class MA>
GenMapRange(const std::tuple<Op,MA>& mapf, const std::shared_ptr<Ranges>&... rs);
Space mSpace;
Op mMapf;
//Op mMapf;
std::shared_ptr<ORType> mOutRange;
Array<size_t,ORType> mMapMult;
vector<size_t> mMapPos;
private:
template <class MA>
void mkOutRange(const MA& mapf);
public:
static constexpr size_t sdim = sizeof...(Ranges);
template <size_t N>
auto get() const -> decltype( *std::get<N>( mSpace ) )&;
template <size_t N>
auto getPtr() const -> decltype( std::get<N>( mSpace ) )&;
std::shared_ptr<ORType> outRange() const;
const Op& map() const;
virtual size_t dim() const final;
virtual size_t size() const final;
virtual SpaceType spaceType() const final;
virtual DataHeader dataHeader() const final;
virtual vector<size_t> typeNum() const final;
virtual size_t cmeta(char* target, size_t pos) const final;
virtual size_t cmetaSize() const final;
virtual std::string stringMeta(size_t pos) const final;
virtual vector<char> data() const final;
const Space& space() const;
virtual IndexType begin() const final;
virtual IndexType end() const final;
const Array<size_t,ORType>& mapMultiplicity() const;
ConstSlice<size_t,GenMapRange> explMapMultiplicity() const;
vector<size_t> mapPos() const;
/*
template <class... ERanges>
auto cat(const std::shared_ptr<GenMapRange<ERanges...> >& erange)
-> std::shared_ptr<GenMapRange<Ranges...,ERanges...> >;
*/
friend GenMapRangeFactory<ORType,Op,XSTYPE,Ranges...>;
static constexpr bool HASMETACONT = false;
static constexpr bool defaultable = false;
static constexpr size_t ISSTATIC = Op::ISSTATIC & (... & Ranges::ISSTATIC);
static constexpr size_t SIZE = Op::SIZE * (... * Ranges::SIZE);
};
// for legacy
template <class OIType, class Op, class... Indices>
using MapIndex = GenMapIndex<OIType,Op,SpaceType::ANY,Indices...>;
template <class ORType, class Op, class... Ranges>
using MapRangeFactory = GenMapRangeFactory<ORType,Op,SpaceType::ANY,Ranges...>;
template <class ORType, class Op, class... Ranges>
using MapRange = GenMapRange<ORType,Op,SpaceType::ANY,Ranges...>;
template <class OIType, class Op, class... Indices>
auto mapResult/*<MapIndex<Op,Indices...> >*/(const std::shared_ptr<MapIndex<OIType,Op,Indices...> >& ind)
-> decltype(ind->outIndex())
{
return ind->outIndex();
}
}
#endif

View file

@ -1,26 +0,0 @@
#ifndef __cxz_map_range_factory_product_map_h__
#define __cxz_map_range_factory_product_map_h__
#include <memory>
#include <vector>
#include <map>
#include "ranges/rbase_def.h"
#include "mbase_def.h"
namespace CNORXZ
{
class MapRangeFactoryProductMap
{
public:
template <class ORType, class MapF, SpaceType XSTYPE, class... Ranges>
friend class GenMapRangeFactory;
private:
static std::map<std::shared_ptr<RangeBase>,vector<std::intptr_t> > mAleadyCreated;
};
}
#endif

View file

@ -1,104 +0,0 @@
#ifndef __cxz_mbase_def_h__
#define __cxz_mbase_def_h__
#include "ranges/rbase_def.h"
#include "allocator.h"
namespace CNORXZ
{
/***********************
* Provided Types *
***********************/
template <class... Ranges>
using ContainerRangeFactory = MultiRangeFactory<Ranges...>;
template <class... Ranges>
using ContainerRange = MultiRange<Ranges...>;
// container_index.h
template <typename T, class... Indices>
class ConstContainerIndex;
// cxz_array.h
template <typename T, class... SRanges>
class ArrayBase;
// cxz_array.h
template <typename T, class... SRanges>
class MutableArrayBase;
// cxz_array.h
template <typename T, class... SRanges>
class Array;
// cxz_operation.h
template <typename T, class OperationClass>
class OperationBase;
// cxz_operation.h
template <typename T, class OperationClass>
class OperationTemplate;
// cxz_operation.h
template <typename T, class... Ranges>
class OperationRoot;
// cxz_operation.h
template <typename T, class... Ranges>
class ParallelOperationRoot;
// cxz_operation.h
template <typename T>
class OperationValue;
// cxz_operation.h
template <typename T, class... Ranges>
class ConstOperationRoot;
// cxz_operation.h
template <typename T, class Op>
class OperationPointer;
// cxz_operation.h
template <typename T, class OpFunction, class... Ops>
class Operation;
// cxz_operation.h
template <typename T, class Op, class IndexType>
class Contraction;
// cxz_operation.h
template <typename T, class Op, class... Indices>
class SliceContraction;
// slice.h
template <typename T, class... SRanges>
class Slice;
template <typename T, class... SRanges>
class ConstSlice;
// slice.h
template <typename T, class... SRanges>
class SliceDef;
// slice.h
template <typename T, class... SRanges>
class ConstSliceDef;
// map_range.h
template <class OITpye, class MapF, SpaceType XSTYPE, class... Indices>
class GenMapIndex;
// map_range.h
template <class ORType, class MapF, SpaceType XSTYPE, class... Ranges>
class GenMapRangeFactory;
// map_range.h
template <class ORType, class MapF, SpaceType XSTYPE, class... Ranges>
class GenMapRange;
}
#endif

View file

@ -0,0 +1,56 @@
// -*- C++ -*-
/**
@file include/memory/allocator.cc.h
@brief Allocator template member function implementation
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_allocator_cc_h__
#define __cxz_allocator_cc_h__
#include "allocator.h"
#include "memcount.h"
namespace CNORXZ
{
template <typename T>
T* Allocator<T>::allocate(SizeT n)
{
const SizeT nn = n*type_size;
MemCount::add(nn);
const SizeT off = nn%N;
const SizeT nnx = (off == 0) ? nn : nn + N - off;
const SizeT nnd = nnx/N;
VX* vx = new VX[nnd];
return reinterpret_cast<T*>(vx);
}
template <typename T>
void Allocator<T>::deallocate(T* p, SizeT n)
{
const SizeT nn = n*type_size;
MemCount::sub(nn);
VX* vx = reinterpret_cast<VX*>(p);
delete [] vx;
}
template <class T, class U>
bool operator==(const Allocator<T>& a, const Allocator<U>& b)
{
return true;
}
template <class T, class U>
bool operator!=(const Allocator<T>& a, const Allocator<U>& b)
{
return false;
}
}
#endif

View file

@ -0,0 +1,85 @@
// -*- C++ -*-
/**
@file include/memory/allocator.h
@brief Allocator declaration
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_allocator__
#define __cxz_allocator__
#include <cstdlib>
#include <new>
#include <vector>
#include <cstdint>
#include <cassert>
#include <iostream>
#include "base/types.h"
#include "base/intrin.h"
#define MIB_SIZE 1024*1024 // 1MiB
#define WARN_SIZE MIB_SIZE*100 // 100 MiB
namespace CNORXZ
{
/** *****
Allocator implementation
Takes care of proper alignment
*/
template <typename T>
class Allocator
{
public:
typedef T value_type;
static constexpr SizeT type_size = sizeof(T); /** < type size */
static constexpr SizeT N = MAX_VSIZE; /** < size of the larges available intrinsics vector */
/** ***
Aligned data block type
The size equals the maximal intrinsics vectors size
*/
struct VX
{
alignas(N) char x[N];
};
/** default constructor */
Allocator() = default;
/** (copy) construct from allocator for different data type
@tparam U input data type
@param x input allocator
*/
template <typename U>
Allocator(const Allocator<U>& x) {}
/** allocate n element of type T
@param n number of elements
*/
T* allocate(SizeT n);
/** deallocate n elements
@param p pointer to first element
@param n number of elements
*/
void deallocate(T* p, SizeT n);
};
/** compare two cnorxz allocators; equality check returns always true */
template <class T, class U>
bool operator==(const Allocator<T>& a, const Allocator<U>& b);
/** compare two cnorxz allocators; unequality check returns always false */
template <class T, class U>
bool operator!=(const Allocator<T>& a, const Allocator<U>& b);
} // namespace CNORXZ
#endif

View file

@ -0,0 +1,53 @@
// -*- C++ -*-
/**
@file include/memory/memcount.h
@brief MemCount declaration.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_memcount_h__
#define __cxz_memcount_h__
#include "base/types.h"
namespace CNORXZ
{
/** *****
Static class to track memory usage by cnorxz types
The usage variable can be changed only be an Allocator instance
@see Allocator
**/
class MemCount
{
private:
static SizeT sMemUsage; /**< current memory usage (bytes) */
/** increas memory usage
@param x number of bytes
*/
static void add(SizeT x);// { sMemUsage += x; }
/** decreas memory usage
@param x number of bytes
*/
static void sub(SizeT x);// { sMemUsage -= x; }
public:
/** no instance construction (static) */
MemCount() = delete;
/** return current memory usage (bytes) */
static SizeT usage();
template <typename T>
friend class Allocator;
};
} // namespace CNORXZ
#endif

View file

@ -0,0 +1,12 @@
// -*- C++ -*-
/**
@file include/memory/memory.cc.h
@brief Memory template implementations main header.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "allocator.cc.h"

View file

@ -0,0 +1,15 @@
// -*- C++ -*-
/**
@file include/memory/memory.h
@brief Memory main heade.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "allocator.h"
#include "memcount.h"
#include "memory.cc.h"

View file

@ -1,72 +0,0 @@
#include "op_expressions.h"
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
/************************
* AssignmentExpr *
************************/
template <OpIndexAff OIA, class ExtType>
inline size_t opIndexResolve(size_t start, ExtType last)
{
if constexpr(OIA == OpIndexAff::EXTERN){
return last.val();
}
if constexpr(OIA == OpIndexAff::TARGET){
return start;
}
return 0;
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::AssignmentExpr(const AccessTemplate<AT>& dataAcc, const Target& tar, const OpClass& sec) :
mTar(tar), mSec(sec), mDataAcc(static_cast<const AT&>(dataAcc)) {}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
inline void AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::operator()(size_t start)
{
ExtType last = rootSteps();
last.zero();
// TODO: ask MA container for data (ptr)!!!
mDataAcc.template exec<Func>(opIndexResolve<OIA>(start,last),mSec,last.next());
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
inline void AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::operator()(size_t start, ExtType last)
{
mDataAcc.template exec<Func>(opIndexResolve<OIA>(start,last),mSec,last.next());
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
typename AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::ExtType
AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::rootSteps(std::intptr_t iPtrNum) const
{
return mTar.rootSteps(iPtrNum).extend( mSec.rootSteps(iPtrNum) );
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
inline void AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::operator()(size_t mlast, DExt last)
{
(*this)(mlast, std::dynamic_pointer_cast<ExtT<ExtType>>(last)->ext());
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
inline DExt AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::dRootSteps(std::intptr_t iPtrNum) const
{
return std::make_shared<ExtT<ExtType>>(rootSteps(iPtrNum));
}
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA>
inline DExt AssignmentExpr<T,Func,AT,Target,OpClass,OIA>::dExtension() const
{
return nullptr; //???!!!
}
} // namespace CNORXZ

View file

@ -1,60 +0,0 @@
#ifndef __cxz_op_expressions__
#define __cxz_op_expressions__
#include "xfor/xfor.h"
#include "access.h"
namespace CNORXZ
{
namespace
{
using namespace CNORXZInternal;
}
enum class OpIndexAff {
EXTERN = 0,
TARGET = 1
};
template <typename T, class Func, class AT, class Target, class OpClass, OpIndexAff OIA=OpIndexAff::EXTERN>
class AssignmentExpr : public ExpressionBase
{
private:
AssignmentExpr() = default;
Target mTar;
OpClass mSec;
AT mDataAcc;
public:
static constexpr size_t LAYER = 0;
static constexpr size_t NHLAYER = 0;
static constexpr size_t SIZE = Target::SIZE + OpClass::SIZE;
typedef decltype(mTar.rootSteps(0).extend( mSec.rootSteps(0) )) ExtType;
AssignmentExpr(const AccessTemplate<AT>& dataAcc, const Target& tar, const OpClass& sec);
AssignmentExpr(const AssignmentExpr& in) = default;
AssignmentExpr(AssignmentExpr&& in) = default;
AssignmentExpr& operator=(const AssignmentExpr& in) = default;
AssignmentExpr& operator=(AssignmentExpr&& in) = default;
virtual std::shared_ptr<ExpressionBase> deepCopy() const override final
{
return std::make_shared<AssignmentExpr<T,Func,AT,Target,OpClass,OIA>>(*this);
}
inline void operator()(size_t start = 0);
inline void operator()(size_t start, ExtType last);
auto rootSteps(std::intptr_t iPtrNum = 0) const -> ExtType;
inline void operator()(size_t mlast, DExt last) override final;
inline DExt dRootSteps(std::intptr_t iPtrNum = 0) const override final;
inline DExt dExtension() const override final;
};
} // namespace CNORXZ
#endif

View file

@ -0,0 +1,109 @@
// -*- C++ -*-
/**
@file include/operation/basic_operations.cc.h
@brief Basic operations implementation
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_basic_operations_cc_h__
#define __cxz_basic_operations_cc_h__
#include "basic_operations.h"
namespace CNORXZ
{
/*==================================+
| standard operatrions (unary) |
+==================================*/
template <class Op>
constexpr decltype(auto) minus(const COpInterface<Op>& op)
{
return operation( [](const auto& a) { return -a; }, op.THIS() );
}
/*===================================+
| standard operatrions (binary) |
+===================================*/
template <class Op1, class Op2>
constexpr decltype(auto) plus(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return operation( [](const auto& a, const auto& b) { return a + b; },
op1.THIS(), op2.THIS() );
}
template <class Op1, class Op2>
constexpr decltype(auto) minus(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return operation( [](const auto& a, const auto& b) { return a - b; },
op1.THIS(), op2.THIS() );
}
template <class Op1, class Op2>
constexpr decltype(auto) multiplies(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return operation( [](const auto& a, const auto& b) { return a * b; },
op1.THIS(), op2.THIS() );
}
template <class Op1, class Op2>
constexpr decltype(auto) divides(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return operation( [](const auto& a, const auto& b) { return a / b; },
op1.THIS(), op2.THIS() );
}
template <class Op1, class Op2>
constexpr decltype(auto) modulo(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return operation( [](const auto& a, const auto& b) { return a % b; },
op1.THIS(), op2.THIS() );
}
/*=======================================+
| operators for standard operations |
+=======================================*/
template <class Op>
constexpr decltype(auto) operator-(const COpInterface<Op>& op)
{
return minus(op);
}
template <class Op1, class Op2>
constexpr decltype(auto) operator+(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return plus(op1, op2);
}
template <class Op1, class Op2>
constexpr decltype(auto) operator-(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return minus(op1, op2);
}
template <class Op1, class Op2>
constexpr decltype(auto) operator*(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return multiplies(op1, op2);
}
template <class Op1, class Op2>
constexpr decltype(auto) operator/(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return divides(op1, op2);
}
template <class Op1, class Op2>
constexpr decltype(auto) operator%(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2)
{
return modulo(op1, op2);
}
}
#endif

View file

@ -0,0 +1,65 @@
// -*- C++ -*-
/**
@file include/operation/basic_operations.h
@brief Basic operations declaration
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_basic_operations_h__
#define __cxz_basic_operations_h__
#include "base/base.h"
#include "operation.h"
namespace CNORXZ
{
// standard operations:
// unary:
template <class Op>
constexpr decltype(auto) minus(const COpInterface<Op>& op);
// binary:
template <class Op1, class Op2>
constexpr decltype(auto) plus(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) minus(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) multiplies(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) divides(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) modulo(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
// operators for standard operations:
template <class Op>
constexpr decltype(auto) operator-(const COpInterface<Op>& op);
template <class Op1, class Op2>
constexpr decltype(auto) operator+(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) operator-(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) operator*(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) operator/(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
template <class Op1, class Op2>
constexpr decltype(auto) operator%(const COpInterface<Op1>& op1, const COpInterface<Op2>& op2);
}
#endif

View file

@ -0,0 +1,279 @@
// -*- C++ -*-
/**
@file include/operation/extensions/avx.cc.h
@brief Register type implementaions for AVX.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_avx_cc_h__
#define __cxz_avx_cc_h__
#include "avx.h"
namespace CNORXZ
{
/*=====================+
| PlusCC / PlusCX |
+=====================*/
inline decltype(auto)
PlusCC<Double,Double,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
inline decltype(auto)
PlusCC<Double,Double,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
PlusCX<Double,X,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const X& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
template <typename X>
inline decltype(auto)
PlusCX<Double,X,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a, const X& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
PlusCX<Double,X,AVX::ND>::eval(const X& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_set1_pd( static_cast<Double>(a) );
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_add_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
/*=======================+
| MinusCC / MinusCX |
+=======================*/
inline decltype(auto)
MinusCC<Double,Double,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_sub_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
inline decltype(auto)
MinusCC<Double,Double,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_sub_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
MinusCX<Double,X,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const X& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_sub_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
template <typename X>
inline decltype(auto)
MinusCX<Double,X,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a, const X& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_sub_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
MinusCX<Double,X,AVX::ND>::eval(const X& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_set1_pd( static_cast<Double>(a) );
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_sub_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
/*=================================+
| MultipliesCC / MultipliesCX |
+=================================*/
inline decltype(auto)
MultipliesCC<Double,Double,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_mul_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
inline decltype(auto)
MultipliesCC<Double,Double,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_mul_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
MultipliesCX<Double,X,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const X& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_mul_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
template <typename X>
inline decltype(auto)
MultipliesCX<Double,X,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a,
const X& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_mul_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
MultipliesCX<Double,X,AVX::ND>::eval(const X& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_set1_pd( static_cast<Double>(a) );
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_mul_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
/*===========================+
| DividesCC / DividesCX |
+===========================*/
inline decltype(auto)
DividesCC<Double,Double,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_div_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
inline decltype(auto)
DividesCC<Double,Double,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a,
const Consecutive<Double,AVX::ND>& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_div_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
DividesCX<Double,X,AVX::ND>::eval(const Consecutive<Double,AVX::ND>& a,
const X& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_div_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
template <typename X>
inline decltype(auto)
DividesCX<Double,X,AVX::ND>::aeval(Consecutive<Double,AVX::ND>& a, const X& b)
{
__m256d av = _mm256_load_pd(a.mD);
__m256d bv = _mm256_set1_pd( static_cast<Double>(b) );
__m256d ov = _mm256_div_pd(av, bv);
_mm256_store_pd(a.mD, ov);
return a;
}
template <typename X>
inline decltype(auto)
DividesCX<Double,X,AVX::ND>::eval(const X& a,
const Consecutive<Double,AVX::ND>& b)
{
Consecutive<Double,AVX::ND> o;
__m256d av = _mm256_set1_pd( static_cast<Double>(a) );
__m256d bv = _mm256_load_pd(b.mD);
__m256d ov = _mm256_div_pd(av, bv);
_mm256_store_pd(o.mD, ov);
return o;
}
}
#endif

View file

@ -0,0 +1,120 @@
// -*- C++ -*-
/**
@file include/operation/extensions/avx.h
@brief Register type specialization for AVX.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_avx_h__
#define __cxz_avx_h__
#include <immintrin.h>
#include "base/base.h"
namespace CNORXZ
{
namespace AVX
{
static constexpr SizeT ND = AVX_VSIZE/sizeof(Double);
static constexpr SizeT NF = AVX_VSIZE/sizeof(float);
}
template <>
struct PlusCC<Double,Double,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
};
template <typename X>
struct PlusCX<Double,X,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
eval(const X& a, const Consecutive<Double,AVX::ND>& b);
};
template <>
struct MinusCC<Double,Double,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
};
template <typename X>
struct MinusCX<Double,X,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
eval(const X& a, const Consecutive<Double,AVX::ND>& b);
};
template <>
struct MultipliesCC<Double,Double,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
};
template <typename X>
struct MultipliesCX<Double,X,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
eval(const X& a, const Consecutive<Double,AVX::ND>& b);
};
template <>
struct DividesCC<Double,Double,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const Consecutive<Double,AVX::ND>& b);
};
template <typename X>
struct DividesCX<Double,X,AVX::ND>
{
static inline decltype(auto)
eval(const Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
aeval(Consecutive<Double,AVX::ND>& a, const X& b);
static inline decltype(auto)
eval(const X& a, const Consecutive<Double,AVX::ND>& b);
};
}
#endif

View file

@ -0,0 +1,21 @@
// -*- C++ -*-
/**
@file include/operation/extensions/extensions.cc.h
@brief Operation extensions template implementations main header.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_extensions_cc_h__
#define __cxz_extensions_cc_h__
#include "reg.cc.h"
#if CXZ_HAVE_AVX
#include "avx.cc.h"
#endif
#endif

View file

@ -0,0 +1,23 @@
// -*- C++ -*-
/**
@file include/operation/extensions/extensions.h
@brief Operation extensions main header.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_extensions_h__
#define __cxz_extensions_h__
#include "reg.h"
#if CXZ_HAVE_AVX
#include "avx.h"
#endif
#include "extensions.cc.h"
#endif

View file

@ -0,0 +1,262 @@
// -*- C++ -*-
/**
@file include/operation/extensions/reg.cc.h
@brief Register type template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_reg_cc_h__
#define __cxz_reg_cc_h__
#include "reg.h"
#include "xpr/pos_type.h"
namespace CNORXZ
{
template <typename T, class EPosT, SizeT... Is>
inline decltype(auto) vregi(const T* d, const EPosT& pos, std::index_sequence<Is...> is)
{
constexpr SizeT N = epos_size<EPosT>::value;
static_assert(N == sizeof...(Is), "got inconsistent index sequence");
return Consecutive<T,N> { d[pos.template get<Is>().val()]... };
}
template <typename T, class EPosT>
inline decltype(auto) vreg(const T* d, const EPosT& pos)
{
constexpr SizeT N = epos_size<EPosT>::value;
static_assert(is_epos_type<EPosT>::value, "got non-epos-type");
if constexpr(pos_type_is_consecutive<EPosT>::value){
return *reinterpret_cast<const Consecutive<T,N>*>(d+pos.scal().val());
}
else {
return vregi(d, pos, std::make_index_sequence<N>{});
}
}
template <typename T, class EPosT>
inline decltype(auto) vreg(T* d, const EPosT& pos)
{
constexpr SizeT N = epos_size<EPosT>::value;
static_assert(is_epos_type<EPosT>::value, "got non-epos-type");
static_assert(pos_type_is_consecutive<EPosT>::value, "no write access for non-consecutive");
if constexpr(pos_type_is_consecutive<EPosT>::value){
return *reinterpret_cast<Consecutive<T,N>*>(d+pos.scal().val());
}
else {
return vregi(d, pos, std::make_index_sequence<N>{});
}
}
template <SizeT I, typename T>
constexpr decltype(auto) consecGet(const T& a)
{
if constexpr(is_consecutive_type<T>::value){
static_assert(I < consecutive_size<T>::value,
"consecutive index out of range");
return a.mD[I];
}
else {
return a;
}
}
template <SizeT I, typename T>
constexpr decltype(auto) consecGet(T& a)
{
if constexpr(is_consecutive_type<T>::value){
static_assert(I < consecutive_size<T>::value,
"consecutive index out of range");
return a.mD[I];
}
else {
return a;
}
}
template <SizeT I, class F, typename... Args>
constexpr decltype(auto) consecApply(const F& f, const Args&... args)
{
return f( consecGet<I>(args)... );
}
template <SizeT I, class F, typename Dst, typename... Args>
constexpr Dst& consecAssign(const F& f, Dst& dst, const Args&... args)
{
f( consecGet<I>(dst), consecGet<I>(args)... );
return dst;
}
template <class F, typename... Args, SizeT... Is>
constexpr decltype(auto) consecFuncI(const F& f, const Args&... args,
std::index_sequence<Is...> is)
{
typedef decltype(consecApply<0>(f, args...)) OType;
constexpr SizeT N = sizeof...(Is);
return Consecutive<OType,N> { consecApply<Is>(f, args...) ... };
}
template <class F, typename Dst, typename... Args, SizeT... Is>
constexpr Dst& consecFuncAI(const F& f, Dst& dst, const Args&... args,
std::index_sequence<Is...> is)
{
( consecAssign<Is>(f, dst, args...), ... );
return dst;
}
template <SizeT N, class F, typename... Args>
constexpr decltype(auto) consecFunc(const F& f, const Args&... args)
{
return consecFuncI<F,Args...>(f, args..., std::make_index_sequence<N>{});
}
template <SizeT N, class F, typename Dst, typename... Args>
constexpr Dst& consecFuncA(const F& f, Dst& dst, const Args&... args)
{
return consecFuncAI<F,Dst,Args...>(f, dst, args..., std::make_index_sequence<N>{});
}
/*============================+
| basic operations: plus |
+============================*/
template <typename T, typename U, SizeT N>
constexpr decltype(auto)
PlusCC<T,U,N>::eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x + y; }, a, b );
}
template <typename T, typename U, SizeT N>
constexpr decltype(auto)
PlusCC<T,U,N>::aeval(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{
return consecFuncA<N>( [](auto& x, const auto& y) { return x += y; }, o, a );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) PlusCX<T,X,N>::eval(const Consecutive<T,N>& a, const X& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x + y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) PlusCX<T,X,N>::eval(const X& a, const Consecutive<T,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x + y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) PlusCX<T,X,N>::aeval(Consecutive<T,N>& o, const X& a)
{
return consecFuncA<N>( [](auto& x, const auto& y) { return x += y; }, o, a );
}
/*=============================+
| basic operations: minus |
+=============================*/
template <typename T, typename U, SizeT N>
constexpr decltype(auto) MinusCC<T,U,N>::eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x - y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MinusCX<T,X,N>::eval(const Consecutive<T,N>& a, const X& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x - y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MinusCX<T,X,N>::eval(const X& a, const Consecutive<T,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x - y; }, a, b );
}
template <typename T, typename U, SizeT N>
constexpr decltype(auto) MinusCC<T,U,N>::aeval(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{
return consecFuncA<N>( [](auto& x, const auto& y) { return x -= y; }, o, a );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MinusCX<T,X,N>::aeval(Consecutive<T,N>& o, const X& a)
{
return consecFuncA<N>( [](auto& x, const auto& y) { return x -= y; }, o, a );
}
/*=================================+
| basic operations: muliplies |
+=================================*/
template <typename T, typename U, SizeT N>
constexpr decltype(auto) MultipliesCC<T,U,N>::eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x * y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MultipliesCX<T,X,N>::eval(const Consecutive<T,N>& a, const X& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x * y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MultipliesCX<T,X,N>::eval(const X& a, const Consecutive<T,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x * y; }, a, b );
}
template <typename T, typename U, SizeT N>
constexpr decltype(auto) MultipliesCC<T,U,N>::aeval(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{
return consecFuncA<N>( [](const auto& x, const auto& y) { return x *= y; }, o, a );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) MultipliesCX<T,X,N>::aeval(Consecutive<T,N>& o, const X& a)
{
return consecFuncA<N>( [](const auto& x, const auto& y) { return x *= y; }, o, a );
}
/*===============================+
| basic operations: divides |
+===============================*/
template <typename T, typename U, SizeT N>
constexpr decltype(auto) DividesCC<T,U,N>::eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x / y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) DividesCX<T,X,N>::eval(const Consecutive<T,N>& a, const X& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x / y; }, a, b );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) DividesCX<T,X,N>::eval(const X& a, const Consecutive<T,N>& b)
{
return consecFunc<N>( [](const auto& x, const auto& y) { return x / y; }, a, b );
}
template <typename T, typename U, SizeT N>
constexpr decltype(auto) DividesCC<T,U,N>::aeval(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{
return consecFuncA<N>( [](const auto& x, const auto& y) { return x /= y; }, o, a );
}
template <typename T, typename X, SizeT N>
constexpr decltype(auto) DividesCX<T,X,N>::aeval(Consecutive<T,N>& o, const X& a)
{
return consecFuncA<N>( [](const auto& x, const auto& y) { return x /= y; }, o, a );
}
}
#endif

View file

@ -0,0 +1,279 @@
// -*- C++ -*-
/**
@file include/operation/extensions/reg.h
@brief Register type declaration.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_reg_h__
#define __cxz_reg_h__
#include "base/base.h"
namespace CNORXZ
{
// no use of Arr = std::array here, since I want ensure that
// it has exactly a memory size of N
template <typename T, SizeT N>
struct Consecutive
{
T mD[N];
};
template <typename T>
struct is_consecutive_type { CXZ_CVAL_FALSE; };
template <typename T>
struct consecutive_base { typedef T type; };
template <typename T>
struct consecutive_size { static constexpr SizeT value = 0; };
template <typename T, SizeT N>
struct is_consecutive_type<Consecutive<T,N>> { CXZ_CVAL_TRUE; };
template <typename T, SizeT N>
struct consecutive_base<Consecutive<T,N>> { typedef T type; };
template <typename T, SizeT N>
struct consecutive_size<Consecutive<T,N>> { static constexpr SizeT value = N; };
/*======================================+
| consecutive generating functions |
+======================================*/
template <typename T, class EPosT, SizeT... Is>
inline decltype(auto) vregi(const T* d, const EPosT& pos, std::index_sequence<Is...> is);
template <typename T, class EPosT>
inline decltype(auto) vreg(const T* d, const EPosT& pos);
template <typename T, class EPosT>
inline decltype(auto) vreg(T* d, const EPosT& pos);
/*================+
| ConsecFunc |
+================*/
template <SizeT I, typename T>
constexpr decltype(auto) consecGet(const T& a);
template <SizeT I, typename T>
constexpr decltype(auto) consecGet(T& a);
template <SizeT I, class F, typename... Args>
constexpr decltype(auto) consecApply(const F& f, const Args&... args);
template <SizeT I, class F, typename Dst, typename... Args>
constexpr Dst& consecAssign(const F& f, Dst& dst, const Args&... args);
template <class F, typename... Args, SizeT... Is>
constexpr decltype(auto) consecFuncI(const F& f, const Args&... args,
std::index_sequence<Is...> is);
template <class F, typename Dst, typename... Args, SizeT... Is>
constexpr Dst& consecFuncAI(const F& f, Dst& dst, const Args&... args,
std::index_sequence<Is...> is);
template <SizeT N, class F, typename... Args>
constexpr decltype(auto) consecFunc(const F& f, const Args&... args);
template <SizeT N, class F, typename Dst, typename... Args>
constexpr Dst& consecFuncA(const F& f, Dst& dst, const Args&... args);
/*============================+
| basic operations: plus |
+============================*/
template <typename T, typename U, SizeT N>
struct PlusCC
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const Consecutive<U,N>& b);
};
template <typename T, typename X, SizeT N>
struct PlusCX
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
eval(const X& a, const Consecutive<T,N>& b);
};
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator+(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{ return PlusCC<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator+(const Consecutive<T,N>& a, const U& b)
{ return PlusCX<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator+(const T& a, const Consecutive<U,N>& b)
{ return PlusCX<U,T,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator+=(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{ return PlusCC<T,U,N>::aeval(o,a); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator+=(Consecutive<T,N>& o, const U& a)
{ return PlusCX<T,U,N>::aeval(o,a); }
/*=============================+
| basic operations: minus |
+=============================*/
template <typename T, typename U, SizeT N>
struct MinusCC
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const Consecutive<U,N>& b);
};
template <typename T, typename X, SizeT N>
struct MinusCX
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
eval(const X& a, const Consecutive<T,N>& b);
};
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator-(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{ return MinusCC<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator-(const Consecutive<T,N>& a, const U& b)
{ return MinusCX<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator-(const T& a, const Consecutive<U,N>& b)
{ return MinusCX<U,T,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator-=(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{ return MinusCC<T,U,N>::eval(o,a); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator-=(Consecutive<T,N>& o, const U& a)
{ return MinusCX<T,U,N>::eval(o,a); }
/*=================================+
| basic operations: muliplies |
+=================================*/
template <typename T, typename U, SizeT N>
struct MultipliesCC
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const Consecutive<U,N>& b);
};
template <typename T, typename X, SizeT N>
struct MultipliesCX
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
eval(const X& a, const Consecutive<T,N>& b);
};
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator*(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{ return MultipliesCC<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator*(const Consecutive<T,N>& a, const U& b)
{ return MultipliesCX<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator*(const T& a, const Consecutive<U,N>& b)
{ return MultipliesCX<U,T,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator*=(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{ return MultipliesCC<T,U,N>::eval(o,a); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator*=(Consecutive<T,N>& o, const U& a)
{ return MultipliesCX<T,U,N>::eval(o,a); }
/*===============================+
| basic operations: divides |
+===============================*/
template <typename T, typename U, SizeT N>
struct DividesCC
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const Consecutive<U,N>& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const Consecutive<U,N>& b);
};
template <typename T, typename X, SizeT N>
struct DividesCX
{
static constexpr decltype(auto)
eval(const Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
aeval(Consecutive<T,N>& a, const X& b);
static constexpr decltype(auto)
eval(const X& a, const Consecutive<T,N>& b);
};
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator/(const Consecutive<T,N>& a, const Consecutive<U,N>& b)
{ return DividesCC<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator/(const Consecutive<T,N>& a, const U& b)
{ return DividesCX<T,U,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr decltype(auto) operator/(const T& a, const Consecutive<U,N>& b)
{ return DividesCX<U,T,N>::eval(a,b); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator/=(Consecutive<T,N>& o, const Consecutive<U,N>& a)
{ return DividesCC<T,U,N>::eval(o,a); }
template <typename T, typename U, SizeT N>
constexpr Consecutive<T,N>& operator/=(Consecutive<T,N>& o, const U& a)
{ return DividesCX<T,U,N>::eval(o,a); }
}
#endif

View file

@ -0,0 +1,515 @@
// -*- C++ -*-
/**
@file include/operation/op_types.cc.h
@brief Operation types template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_op_types_cc_h__
#define __cxz_op_types_cc_h__
#include "op_types.h"
#include "op_utility.h"
#include "extensions/extensions.h"
namespace CNORXZ
{
/*====================+
| COpInterface |
+====================*/
template <class OpT>
template <class F, class IndexT>
constexpr decltype(auto) COpInterface<OpT>::c(F&& f, const Sptr<IndexT>& ind) const
{
return contraction(std::forward<F>(f), THIS().r(), ind);
}
template <class OpT>
template <class IndexT>
constexpr decltype(auto) COpInterface<OpT>::c(const Sptr<IndexT>& ind) const
{
return contraction([](auto& a, const auto& b) { a += b; },
THIS(), ind);
}
template <class OpT>
template <class F, class... Args>
constexpr decltype(auto) COpInterface<OpT>::o(F&& f, Args&&... args) const
{
return operation(std::forward<F>(f), THIS().r(), args...);
}
/*===================+
| OpInterface |
+===================*/
template <class OpT>
template <class IndexT, class F, class... Args>
constexpr decltype(auto) OpInterface<OpT>::ax(const Sptr<IndexT>& ind, F&& f, const Args&... args)
{
return ind->ifor( operation(f, OI::THIS().r(), args...), NoF {} );
}
template <class OpT>
template <class IndexT, class F, class... Args>
inline void OpInterface<OpT>::a(const Sptr<IndexT>& ind, F&& f, const Args&... args)
{
ax(ind, f, args...)();
}
/*=============+
| COpRoot |
+=============*/
template <typename T, class IndexT>
constexpr COpRoot<T,IndexT>::COpRoot(const CArrayBase<T>& a, const Sptr<IndexT>& ind) :
mData(a.data()+ind->pos()),
mIndex(ind)
{}
template <typename T, class IndexT>
constexpr COpRoot<T,IndexT>::COpRoot(const T* data, const Sptr<IndexT>& ind) :
mData(data+ind->pos()),
mIndex(ind)
{}
template <typename T, class IndexT>
constexpr COpRoot<T,IndexT>& COpRoot<T,IndexT>::init(const T* data, const Sptr<IndexT>& ind)
{
mData = data+ind->pos();
mIndex = ind;
return *this;
}
template <typename T, class IndexT>
template <class PosT>
constexpr decltype(auto) COpRoot<T,IndexT>::operator()(const PosT& pos) const
{
if constexpr(is_epos_type<PosT>::value){
return vreg(mData,pos); // distinguish between consecutive/non-consecutive
}
else {
return mData[pos.val()];
}
}
template <typename T, class IndexT>
constexpr decltype(auto) COpRoot<T,IndexT>::operator()() const
{
return mData[0];
}
template <typename T, class IndexT>
template <SizeT I>
constexpr decltype(auto) COpRoot<T,IndexT>::rootSteps(const IndexId<I>& id) const
{
return mIndex->stepSize(id);
}
template <typename T, class IndexT>
const T* COpRoot<T,IndexT>::data() const
{
return mData;
}
template <typename T, class IndexT>
constexpr decltype(auto) coproot(const CArrayBase<T>& a, const Sptr<IndexT>& ind)
{
return COpRoot<T,IndexT>(a, ind);
}
template <typename T, class IndexT>
constexpr decltype(auto) coproot(const T* a, const Sptr<IndexT>& ind)
{
return COpRoot<T,IndexT>(a, ind);
}
/*=============+
| POpRoot |
+=============*/
template <class IndexT, class Op>
constexpr POpRoot<IndexT,Op>::POpRoot(const Sptr<IndexT>& ind, const SizeT* parts, Op&& op) :
mIndex(ind),
mFp(1,parts),
mOp(std::forward<Op>(op))
{}
template <class IndexT, class Op>
template <class PosT>
constexpr decltype(auto) POpRoot<IndexT,Op>::operator()(const PosT& pos) const
{
return mOp(mFp(pos));
}
template <class IndexT, class Op>
constexpr decltype(auto) POpRoot<IndexT,Op>::operator()() const
{
return mOp(mFp(SPos<0>()));
}
template <class IndexT, class Op>
template <SizeT I>
constexpr decltype(auto) POpRoot<IndexT,Op>::rootSteps(const IndexId<I>& id) const
{
return mIndex->stepSize(id);
}
template <class IndexT, class Op>
constexpr decltype(auto) POpRoot<IndexT,Op>::data() const
{
return mOp->data();
}
template <class IndexT, class Op>
constexpr decltype(auto) poproot(const Sptr<IndexT>& ind, const SizeT* parts, Op&& op)
{
return POpRoot(ind, parts, std::forward<Op>(op));
}
/*==============+
| OpCont |
+==============*/
template <typename T, class IndexT>
constexpr OpCont<T,IndexT>::OpCont(const Sptr<IndexT>& ind) :
mIndex(ind),
mC(std::make_shared<Vector<T>>(mIndex->pmax().val()))
{}
template <typename T, class IndexT>
constexpr OpCont<T,IndexT>& OpCont<T,IndexT>::init(const Sptr<IndexT>& ind)
{
mIndex = ind;
if(mC.size() != mIndex->pmax().val()){
mC.resize(mIndex->pmax().val());
}
return *this;
}
template <typename T, class IndexT>
constexpr OpCont<T,IndexT>& OpCont<T,IndexT>::init(const Sptr<IndexT>& ind,
const Vector<T>& c)
{
init(ind);
CXZ_ASSERT(c.size() == mC.size(),
"size-mismatch: expected " << mC.size() << ", got " << c.size());
std::transform(c.begin(), c.end(), mC.begin(), [](const auto& x) { return x; } );
return *this;
}
template <typename T, class IndexT>
constexpr decltype(auto) OpCont<T,IndexT>::r()
{
return OpRoot<T,IndexT>(data(), mIndex);
}
template <typename T, class IndexT>
constexpr decltype(auto) OpCont<T,IndexT>::r() const
{
return COpRoot<T,IndexT>(data(), mIndex);
}
template <typename T, class IndexT>
template <class Op>
constexpr OpCont<T,IndexT>& OpCont<T,IndexT>::operator=(const Op& o)
{
// TODO: build and execute assign expression forwarding outer index
// if a1 and a2 are non-expression types (like it is the case now),
// just do what is currently implemented
OI::a(mIndex, [](auto& a1, const auto& a2) { a1 = a2; }, o);
return *this;
}
template <typename T, class IndexT>
template <class Op>
constexpr OpCont<T,IndexT>& OpCont<T,IndexT>::operator+=(const Op& o)
{
OI::a(mIndex, [](auto& a1, const auto& a2) { a1 += a2; }, o);
return *this;
}
template <typename T, class IndexT>
constexpr OpCont<T,IndexT>& OpCont<T,IndexT>::operator=(const OpCont<T,IndexT>& o)
{
OI::a(mIndex, [](auto& a1, const auto& a2) { a1 = a2; }, o);
return *this;
}
template <typename T, class IndexT>
template <class PosT>
constexpr decltype(auto) OpCont<T,IndexT>::operator()(const PosT& pos) const
{
if constexpr(is_epos_type<PosT>::value){
if constexpr(pos_type_is_consecutive<PosT>::value){
return vreg(mC.data(),pos);
}
else {
// non-consecutive data cannot be directly accessed
// so there is no non-const (write) access!
return vreg(const_cast<const T*>(mC.data()),pos);
}
}
else {
return mC[pos.val()];
}
}
template <typename T, class IndexT>
constexpr decltype(auto) OpCont<T,IndexT>::operator()() const
{
return mC[0];
}
template <typename T, class IndexT>
template <SizeT I>
constexpr decltype(auto) OpCont<T,IndexT>::rootSteps(const IndexId<I>& id) const
{
return mIndex->stepSize(id);
}
template <typename T, class IndexT>
T* OpCont<T,IndexT>::data()
{
return mC.data();
}
template <typename T, class IndexT>
const T* OpCont<T,IndexT>::data() const
{
return mC.data();
}
/*==============+
| OpRoot |
+==============*/
template <typename T, class IndexT>
constexpr OpRoot<T,IndexT>::OpRoot(ArrayBase<T>& a, const Sptr<IndexT>& ind) :
mData(a.data()+ind->pos()),
mIndex(ind)
{}
template <typename T, class IndexT>
constexpr OpRoot<T,IndexT>::OpRoot(T* data, const Sptr<IndexT>& ind) :
mData(data+ind->pos()),
mIndex(ind)
{}
template <typename T, class IndexT>
constexpr OpRoot<T,IndexT>& OpRoot<T,IndexT>::init(T* data, const Sptr<IndexT>& ind)
{
mData = data+ind->pos();
mIndex = ind;
return *this;
}
template <typename T, class IndexT>
template <class Op>
constexpr OpRoot<T,IndexT>& OpRoot<T,IndexT>::operator=(const Op& o)
{
OI::a(mIndex, [](auto& a, const auto& b) { a = b; }, o);
return *this;
}
template <typename T, class IndexT>
template <class Op>
constexpr OpRoot<T,IndexT>& OpRoot<T,IndexT>::operator+=(const Op& o)
{
OI::a(mIndex, [](auto& a, const auto& b) { a += b; }, o);
return *this;
}
template <typename T, class IndexT>
constexpr OpRoot<T,IndexT>& OpRoot<T,IndexT>::operator=(const OpRoot<T,IndexT>& o)
{
OI::a(mIndex, [](auto& a, const auto& b) { a = b; }, o);
return *this;
}
template <typename T, class IndexT>
template <class PosT>
constexpr decltype(auto) OpRoot<T,IndexT>::operator()(const PosT& pos) const
{
if constexpr(is_epos_type<PosT>::value){
if constexpr(pos_type_is_consecutive<PosT>::value){
return vreg(mData,pos);
}
else {
// non-consecutive data cannot be directly accessed
// so there is no non-const (write) access!
return vreg(const_cast<const T*>(mData),pos);
}
}
else {
return mData[pos.val()];
}
}
template <typename T, class IndexT>
constexpr decltype(auto) OpRoot<T,IndexT>::operator()() const
{
return mData[0];
}
template <typename T, class IndexT>
template <SizeT I>
constexpr decltype(auto) OpRoot<T,IndexT>::rootSteps(const IndexId<I>& id) const
{
return mIndex->stepSize(id);
}
template <typename T, class IndexT>
T* OpRoot<T,IndexT>::data() const
{
return mData;
}
template <typename T, class IndexT>
constexpr decltype(auto) oproot(ArrayBase<T>& a, const Sptr<IndexT>& ind)
{
return OpRoot<T,IndexT>(a, ind);
}
/*=================+
| Operation |
+=================*/
template <class F, class... Ops>
constexpr Operation<F,Ops...>::Operation(F&& f, const Ops&... ops) :
mOps(ops...),
mF(std::forward<F>(f))
{}
template <class F, class... Ops>
template <class PosT>
constexpr decltype(auto) Operation<F,Ops...>::operator()(const PosT& pos) const
{
return pos_unpack_args(mF, pos, mOps);
}
template <class F, class... Ops>
constexpr decltype(auto) Operation<F,Ops...>::operator()() const
{
return exec(std::make_index_sequence<sizeof...(Ops)>{});
}
template <class F, class... Ops>
template <SizeT I>
constexpr decltype(auto) Operation<F,Ops...>::rootSteps(const IndexId<I>& id) const
{
return rootStepsi(id, std::make_index_sequence<sizeof...(Ops)>{});
}
template <class F, class... Ops>
template <SizeT... Is>
constexpr decltype(auto) Operation<F,Ops...>::exec(std::index_sequence<Is...> is) const
{
return mF( std::get<Is>(mOps)() ... );
}
template <class F, class... Ops>
template <SizeT I, SizeT... Is>
constexpr decltype(auto) Operation<F,Ops...>::rootStepsi(const IndexId<I>& id,
std::index_sequence<Is...> is) const
{
return ( std::get<Is>(mOps).rootSteps(id) << ... );
}
template <class F, class... Ops>
constexpr decltype(auto) operation(F&& f, const Ops&... ops)
{
return Operation<F,Ops...>(std::forward<F>(f), ops...);
}
template <class Tar, class Src>
constexpr decltype(auto) assignxpr(const Tar& tar, const Src& src)
{
static_assert(is_xpr<Tar>::value, "expected expression");
if constexpr(is_xpr<Src>::value){
return operation([](auto& a, const auto& b) { a = b; }, tar, src);
}
else {
return operation([&](auto& a) { a = src; }, tar);
}
}
template <class Tar, class Src>
constexpr decltype(auto) assignxpr(Tar& tar, const Src& src)
{
if constexpr(is_xpr<Tar>::value){
if constexpr(is_xpr<Src>::value){
return operation([](auto& a, const auto& b) { a = b; }, tar, src);
}
else {
return operation([&](auto& a) { a = src; }, tar);
}
}
else {
if constexpr(is_xpr<Src>::value){
return operation([&](const auto& b) { tar = b; }, src);
}
else {
return operation([&]() { tar = src; });
}
}
}
/*===================+
| Contraction |
+===================*/
template <class CXpr>
constexpr Contraction<CXpr>::Contraction(CXpr&& cxpr) :
mCXpr(cxpr)
{}
template <class CXpr>
template <class PosT>
constexpr decltype(auto) Contraction<CXpr>::operator()(const PosT& pos) const
{
return mCXpr(pos);
}
template <class CXpr>
constexpr decltype(auto) Contraction<CXpr>::operator()() const
{
return mCXpr();
}
template <class CXpr>
template <SizeT I>
constexpr decltype(auto) Contraction<CXpr>::rootSteps(const IndexId<I>& id) const
{
return mCXpr.rootSteps(id);
}
template <class F, class Op, class IndexT>
constexpr decltype(auto) contraction(F&& f, Op&& op, const Sptr<IndexT>& i)
{
typedef decltype(i->ifor( op, f )) CXprT; // TODO: implement ifor with func arg!!!
return Contraction<CXprT>( i->ifor( op, f ) );
}
/*======================+
| various functions |
+======================*/
template <class IndexT>
constexpr decltype(auto) indexOp(const Sptr<IndexT>& i)
{
return i->xpr(i);
}
}
#endif

View file

@ -0,0 +1,298 @@
// -*- C++ -*-
/**
@file include/operation/op_types.h
@brief Operation types declarations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_op_types_h__
#define __cxz_op_types_h__
#include "base/base.h"
#include "xpr/xpr_base.h"
#include "array/array_base.h"
namespace CNORXZ
{
template <class OpT>
class COpInterface : public XprInterface<OpT>
{
public:
constexpr COpInterface() = default;
OpT& THIS() { return static_cast<OpT&>(*this); }
const OpT& THIS() const { return static_cast<const OpT&>(*this); }
constexpr decltype(auto) r() { return THIS(); }
constexpr decltype(auto) r() const { return THIS(); }
template <class F, class IndexT>
constexpr decltype(auto) c(F&& f, const Sptr<IndexT>& ind) const;
template <class IndexT>
constexpr decltype(auto) c(const Sptr<IndexT>& ind) const;
template <class F, class... Args>
constexpr decltype(auto) o(F&& f, Args&&... args) const;
};
template <class OpT>
class OpInterface : public COpInterface<OpT>
{
public:
typedef COpInterface<OpT> OI;
constexpr OpInterface() = default;
OpT& THIS() { return static_cast<OpT&>(*this); }
const OpT& THIS() const { return static_cast<const OpT&>(*this); }
template <class IndexT, class F, class... Args>
constexpr decltype(auto) ax(const Sptr<IndexT>& ind, F&& f, const Args&... args);
template <class IndexT, class F, class... Args>
inline void a(const Sptr<IndexT>& ind, F&& f, const Args&... args);
};
template <class T>
struct is_operation
{ static constexpr bool value = std::is_base_of<COpInterface<T>,T>::value; };
template <class T>
struct is_mutable_operation
{ static constexpr bool value = std::is_base_of<OpInterface<T>,T>::value; };
template <class T>
struct op_size
{ static constexpr SizeT value = is_operation<T>::value ? 1 : 0; };
template <typename T, class IndexT>
class COpRoot : public COpInterface<COpRoot<T,IndexT>>
{
public:
typedef OpInterface<COpRoot<T,IndexT>> OI;
constexpr COpRoot() = default;
constexpr COpRoot(const CArrayBase<T>& a, const Sptr<IndexT>& ind);
constexpr COpRoot(const T* data, const Sptr<IndexT>& ind);
constexpr COpRoot& init(const T* data, const Sptr<IndexT>& ind);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
const T* data() const;
private:
const T* mData = nullptr;
Sptr<IndexT> mIndex;
};
template <typename T, class IndexT>
constexpr decltype(auto) coproot(const CArrayBase<T>& a, const Sptr<IndexT>& ind);
template <typename T, class IndexT>
constexpr decltype(auto) coproot(const T* a, const Sptr<IndexT>& ind);
template <class IndexT, class Op>
class POpRoot : public COpInterface<POpRoot<IndexT,Op>>
{
public:
typedef COpInterface<POpRoot<IndexT,Op>> OI;
constexpr POpRoot() = default;
constexpr POpRoot(const Sptr<IndexT>& ind, const SizeT* parts, Op&& op);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
constexpr decltype(auto) data() const;
private:
Sptr<IndexT> mIndex;
FPos mFp;
Op mOp;
};
template <class IndexT, class Op>
constexpr decltype(auto) poproot(const Sptr<IndexT>& ind, const SizeT* parts, Op&& op);
template <typename T, class IndexT>
class OpCont : public OpInterface<OpCont<T,IndexT>>
{
public:
typedef OpInterface<OpCont<T,IndexT>> OI;
typedef typename Container<T,index_const_size<IndexT>::value,
index_has_const_size<IndexT>::value>::type CT;
constexpr OpCont() = default;
constexpr OpCont(const Sptr<IndexT>& ind);
constexpr OpCont& init(const Sptr<IndexT>& ind);
constexpr OpCont& init(const Sptr<IndexT>& ind, const Vector<T>& c);
constexpr decltype(auto) r();
constexpr decltype(auto) r() const;
template <class Op>
constexpr OpCont& operator=(const Op& in);
template <class Op>
constexpr OpCont& operator+=(const Op& in);
constexpr OpCont& operator=(const OpCont& in);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
T* data();
const T* data() const;
private:
Sptr<IndexT> mIndex;
CT mC;
};
template <typename T, class IndexT>
class OpRoot : public OpInterface<OpRoot<T,IndexT>>
{
public:
typedef OpInterface<OpRoot<T,IndexT>> OI;
constexpr OpRoot() = default;
constexpr OpRoot(ArrayBase<T>& a, const Sptr<IndexT>& ind);
constexpr OpRoot(T* data, const Sptr<IndexT>& ind);
constexpr OpRoot& init(T* data, const Sptr<IndexT>& ind);
template <class Op>
constexpr OpRoot& operator=(const Op& in);
template <class Op>
constexpr OpRoot& operator+=(const Op& in);
constexpr OpRoot& operator=(const OpRoot& in);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
T* data() const;
private:
T* mData = nullptr;
Sptr<IndexT> mIndex;
};
template <typename T, class IndexT>
constexpr decltype(auto) oproot(ArrayBase<T>& a, const Sptr<IndexT>& ind);
template <class F, class... Ops>
class Operation : public OpInterface<Operation<F,Ops...>>
{
public:
typedef OpInterface<Operation<F,Ops...>> OI;
constexpr Operation() = default;
constexpr Operation(F&& f, const Ops&... ops);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
private:
template <SizeT... Is>
constexpr decltype(auto) exec(std::index_sequence<Is...> is) const;
template <SizeT I, SizeT... Is>
constexpr decltype(auto) rootStepsi(const IndexId<I>& id,
std::index_sequence<Is...> is) const;
Tuple<Ops...> mOps;
F mF;
};
template <class F, class... Ops>
constexpr decltype(auto) operation(F&& f, const Ops&... ops);
template <class Tar, class Src>
constexpr decltype(auto) assignxpr(const Tar& tar, const Src& src);
template <class Tar, class Src>
constexpr decltype(auto) assignxpr(Tar& tar, const Src& src);
template <class F, class... Ops>
struct op_size<Operation<F,Ops...>>
{ static constexpr SizeT value = ( op_size<Ops>::value + ... ); };
template <class CXpr>
class Contraction : public OpInterface<Contraction<CXpr>>
{
public:
typedef OpInterface<Contraction<CXpr>> OI;
constexpr Contraction() = default;
constexpr Contraction(CXpr&& cxpr);
template <class PosT>
constexpr decltype(auto) operator()(const PosT& pos) const;
constexpr decltype(auto) operator()() const;
template <SizeT I>
constexpr decltype(auto) rootSteps(const IndexId<I>& id) const;
private:
CXpr mCXpr;
};
template <class CXpr>
struct op_size<Contraction<CXpr>>
{ static constexpr SizeT value = op_size<CXpr>::value; };
template <class F, class Op, class IndexT>
constexpr decltype(auto) contraction(F&& f, Op&& op, const Sptr<IndexT>& i);
template <class IndexT>
constexpr decltype(auto) indexOp(const Sptr<IndexT>& i);
}
#endif

View file

@ -0,0 +1,63 @@
// -*- C++ -*-
/**
@file include/operation/op_utility.cc.h
@brief Operation utilities template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_op_utility_cc_h__
#define __cxz_op_utility_cc_h__
#include "op_utility.h"
#include "xpr/pos_type.h"
namespace CNORXZ
{
template <SizeT I, class PosT>
constexpr decltype(auto) pos_get(const PosT& pos)
{
static_assert(I < static_pos_size<PosT>::value, "index out of range");
if constexpr(I == 0){
return pos;
}
else {
return pos_get<I-1>(pos.next());
}
}
template <SizeT J, SizeT I, SizeT... Is>
constexpr SizeT sum_index_sequence(std::index_sequence<I,Is...> is)
{
static_assert(J < sizeof...(Is)+1, "index out of range");
if constexpr(J == 0){
return 0;
}
else {
return sum_index_sequence<J-1>(std::index_sequence<Is...>{}) + I;
}
}
template <class F, class PosT, class OpTuple, class OpSizes, SizeT... Is>
inline auto pos_unpack_args_i(const F& f, const PosT& pos, const OpTuple& args,
OpSizes opsizes, std::index_sequence<Is...> is)
{
return f(std::get<Is>(args)(pos_get<sum_index_sequence<Is>(opsizes)>(pos))...);
}
template <class F, class PosT, class... Ops>
inline auto pos_unpack_args(const F& f, const PosT& pos, const Tuple<Ops...>& args)
{
static_assert(is_pos_type<PosT>::value, "got non-pos-type");
static_assert((is_operation<Ops>::value and ...), "got non-operation type");
typedef std::make_index_sequence<sizeof...(Ops)> Idxs;
typedef std::index_sequence<op_size<Ops>::value...> OpSizes;
return pos_unpack_args_i(f, pos, args, OpSizes{}, Idxs{});
}
}
#endif

View file

@ -0,0 +1,34 @@
// -*- C++ -*-
/**
@file include/operation/op_utility.h
@brief Operation utilities declarations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#ifndef __cxz_op_utility_h__
#define __cxz_op_utility_h__
#include "base/base.h"
namespace CNORXZ
{
template <SizeT I, class PosT>
constexpr decltype(auto) pos_get(const PosT& pos);
template <SizeT J, SizeT... Is>
constexpr SizeT sum_index_sequence(std::index_sequence<Is...> is);
template <class F, class PosT, class OpTuple, class OpSizes, SizeT... Is>
inline auto pos_unpack_args_i(const F& f, const PosT& pos, const OpTuple& args,
OpSizes opsizes, std::index_sequence<Is...> is);
template <class F, class PosT, class... Ops>
inline auto pos_unpack_args(const F& f, const PosT& pos, const Tuple<Ops...>& args);
}
#endif

View file

@ -0,0 +1,14 @@
// -*- C++ -*-
/**
@file include/operation/operation.cc.h
@brief Operation main header for template implementations.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "op_types.cc.h"
#include "op_utility.cc.h"
#include "basic_operations.cc.h"

View file

@ -0,0 +1,16 @@
// -*- C++ -*-
/**
@file include/operation/operation.h
@brief Operation main header.
Copyright (c) 2024 Christian Zimmermann. All rights reserved.
Mail: chizeta@f3l.de
**/
#include "op_types.h"
#include "op_utility.h"
#include "basic_operations.h"
#include "operation.cc.h"

View file

@ -1,94 +0,0 @@
#ifndef __cxz_operation_def_h__
#define __cxz_operation_def_h__
#include "cxz_operation.h"
namespace CNORXZ
{
template <typename T, class OperationClass>
auto operator+(const T& a, const OperationBase<T,OperationClass>& b)
-> Operation<T,plus<T>,OperationValue<T>,OperationClass>
{
OperationValue<T> v(a);
return Operation<T,plus<T>,OperationValue<T>,OperationClass>(v, b.THIS());
}
template <typename T, class OperationClass>
auto operator-(const T& a, const OperationBase<T,OperationClass>& b)
-> Operation<T,minus<T>,OperationValue<T>,OperationClass>
{
OperationValue<T> v(a);
return Operation<T,minus<T>,OperationValue<T>,OperationClass>(v, b.THIS());
}
template <typename T, class OperationClass>
auto operator*(const T& a, const OperationBase<T,OperationClass>& b)
-> Operation<T,multiplies<T>,OperationValue<T>,OperationClass>
{
OperationValue<T> v(a);
return Operation<T,multiplies<T>,OperationValue<T>,OperationClass>(v, b.THIS());
}
template <typename T, class OperationClass>
auto operator/(const T& a, const OperationBase<T,OperationClass>& b)
-> Operation<T,divides<T>,OperationValue<T>,OperationClass>
{
OperationValue<T> v(a);
return Operation<T,divides<T>,OperationValue<T>,OperationClass>(v, b.THIS());
}
template <typename T, class OperationClass>
auto operator+(const OperationBase<T,OperationClass>& a, const T& b)
-> Operation<T,plus<T>,OperationClass,OperationValue<T> >
{
OperationValue<T> v(b);
return Operation<T,plus<T>,OperationClass,OperationValue<T> >(a.THIS(), v);
}
template <typename T, class OperationClass>
auto operator-(const OperationBase<T,OperationClass>& a, const T& b)
-> Operation<T,minus<T>,OperationClass,OperationValue<T> >
{
OperationValue<T> v(b);
return Operation<T,minus<T>,OperationClass,OperationValue<T> >(a.THIS(), v);
}
template <typename T, class OperationClass>
auto operator*(const OperationBase<T,OperationClass>& a, const T& b)
-> Operation<T,multiplies<T>,OperationClass,OperationValue<T> >
{
OperationValue<T> v(b);
return Operation<T,multiplies<T>,OperationClass,OperationValue<T> >(a.THIS(), v);
}
template <typename T, class OperationClass>
auto operator/(const OperationBase<T,OperationClass>& a, const T& b)
-> Operation<T,divides<T>,OperationClass,OperationValue<T> >
{
OperationValue<T> v(b);
return Operation<T,divides<T>,OperationClass,OperationValue<T> >(a.THIS(), v);
}
#define regFunc1(fff) template <typename T, class OperationClass> \
auto fff(const OperationBase<T,OperationClass>& a) \
-> Operation<T,x_##fff<T>,OperationClass> { \
return Operation<T,x_##fff<T>,OperationClass>(a.THIS()); }
#include "extensions/math.h"
#undef regFunc1
template <size_t N, typename T, class OperationClass>
auto ipow(const OperationBase<T,OperationClass>& a)
-> Operation<T,x_ipow<N-1>,OperationClass>
{
return Operation<T,x_ipow<N-1>,OperationClass>(a.THIS());
}
}
#endif

Some files were not shown because too many files have changed in this diff Show more