num4simdiff 0.1.1 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +6 -0
- data/ext/num4simdiff/CNum4SimDiff.c +30 -30
- data/ext/num4simdiff/CNum4SimDiff.h +6 -9
- data/lib/num4simdiff.rb +46 -34
- metadata +4 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 61244490a74e2b2b27f14967ce4d45cc073cfe2323021a488babcd39f921995b
|
4
|
+
data.tar.gz: 57b1d91fa1b8e7c1e0114eb749722f9a25a5bb60613608a4b5db30f8a375910a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f3f0e6cc7764903302b93212e93b58e46a04703950c229bb9e3775bf4cd28a90e1d8f18010f9007c25b762ce76c005f97bb1e19f45a46c4aa72c14c50819248b
|
7
|
+
data.tar.gz: f60265b9f41b006209937b8cf055ff7043658033dd66fc92c48f9e098fecbd599c8d5c9cd442dd98e002a251be422338bbbb6b20448c99eaa7a6217995b14bd0
|
data/CHANGELOG.md
CHANGED
@@ -4,12 +4,10 @@
|
|
4
4
|
#include <stdlib.h>
|
5
5
|
#include "CNum4SimDiff.h"
|
6
6
|
|
7
|
-
static double*
|
8
|
-
static double*
|
9
|
-
static double*
|
10
|
-
static double* CNum4SimDiff_doRungeKuttaMethod(int n, double *yi, double h, Func func);
|
7
|
+
static double* CNum4SimDiff_doEulerMethod(int n, double *yi, double h, double *f);
|
8
|
+
static double* CNum4SimDiff_doHeunMethod(int n, double *yi, double h, double *f);
|
9
|
+
static double* CNum4SimDiff_doRungeKuttaMethod(int n, double *yi, double h, double *f);
|
11
10
|
static CNum4SimDiff _cNum4SiDiff = {
|
12
|
-
.FP_dmy = CNum4SimDiff_doDmy,
|
13
11
|
.FP_eulerMethod = CNum4SimDiff_doEulerMethod,
|
14
12
|
.FP_heunMethod = CNum4SimDiff_doHeunMethod,
|
15
13
|
.FP_rungeKuttaMethod = CNum4SimDiff_doRungeKuttaMethod,
|
@@ -20,46 +18,42 @@ static CNum4SimDiff _cNum4SiDiff = {
|
|
20
18
|
/**************************************/
|
21
19
|
/* Class部 */
|
22
20
|
/**************************************/
|
23
|
-
double*
|
21
|
+
double* CNum4SimDiff_eulerMethod(int n, double *yi, double h, double *f)
|
24
22
|
{
|
25
|
-
assert(
|
23
|
+
assert(f != 0);
|
24
|
+
assert(yi != 0);
|
25
|
+
assert( n > 0);
|
26
26
|
|
27
|
-
return _cNum4SiDiff.
|
27
|
+
return _cNum4SiDiff.FP_eulerMethod(n, yi, h, f);
|
28
28
|
}
|
29
|
-
double*
|
29
|
+
double* CNum4SimDiff_heunMethod(int n, double *yi, double h, double *f)
|
30
30
|
{
|
31
|
-
assert(
|
31
|
+
assert(f != 0);
|
32
|
+
assert(yi != 0);
|
33
|
+
assert( n > 0);
|
32
34
|
|
33
|
-
return _cNum4SiDiff.
|
35
|
+
return _cNum4SiDiff.FP_heunMethod(n, yi, h, f);
|
34
36
|
}
|
35
|
-
double*
|
37
|
+
double* CNum4SimDiff_rungeKuttaMethod(int n, double *yi, double h, double *f)
|
36
38
|
{
|
37
|
-
assert(
|
39
|
+
assert(f != 0);
|
40
|
+
assert(yi != 0);
|
41
|
+
assert( n > 0);
|
38
42
|
|
39
|
-
return _cNum4SiDiff.
|
40
|
-
}
|
41
|
-
double* CNum4SimDiff_rungeKuttaMethod(int n, double *yi, double h, Func func)
|
42
|
-
{
|
43
|
-
assert(func != 0);
|
44
|
-
|
45
|
-
return _cNum4SiDiff.FP_rungeKuttaMethod(n, yi, h, func);
|
43
|
+
return _cNum4SiDiff.FP_rungeKuttaMethod(n, yi, h, f);
|
46
44
|
}
|
47
45
|
/**************************************/
|
48
46
|
/* 処理実行部 */
|
49
47
|
/**************************************/
|
50
|
-
static double* CNum4SimDiff_doDmy(int n, double *yi, double h, Func func)
|
51
|
-
{
|
52
|
-
return func(2, yi);
|
53
|
-
}
|
54
48
|
/*
|
55
49
|
* オイラー法
|
56
50
|
*/
|
57
|
-
static double* CNum4SimDiff_doEulerMethod(int n, double *yi, double h,
|
51
|
+
static double* CNum4SimDiff_doEulerMethod(int n, double *yi, double h, double *f)
|
58
52
|
{
|
59
53
|
int i;
|
60
|
-
double *f = func(n, yi);
|
61
54
|
double *yi_1 = malloc(sizeof(double) * n);
|
62
55
|
|
56
|
+
assert(yi_1 != 0);
|
63
57
|
// yi_1 = yi + h * f(xi, y)
|
64
58
|
for (i = 0; i < n; i++) {
|
65
59
|
yi_1[i] = yi[i] + h * f[i];
|
@@ -69,14 +63,16 @@ static double* CNum4SimDiff_doEulerMethod(int n, double *yi, double h, Func func
|
|
69
63
|
/*
|
70
64
|
* ホイン法
|
71
65
|
*/
|
72
|
-
static double* CNum4SimDiff_doHeunMethod(int n, double *yi, double h,
|
66
|
+
static double* CNum4SimDiff_doHeunMethod(int n, double *yi, double h, double *f)
|
73
67
|
{
|
74
68
|
int i;
|
75
|
-
double *f = func(n, yi);
|
76
69
|
double *yi_1 = malloc(sizeof(double) * n);
|
77
70
|
double *k1 = malloc(sizeof(double) * n);
|
78
71
|
double *k2 = malloc(sizeof(double) * n);
|
79
72
|
|
73
|
+
assert(yi_1 != 0);
|
74
|
+
assert(k1 != 0);
|
75
|
+
assert(k2 != 0);
|
80
76
|
// k1 = h * f(xi, y)
|
81
77
|
// k2 = h * f(xi + h, h * f(xi + h, yi + k1)
|
82
78
|
// yi_1 = yi + (k1 + k2) / 2.0;
|
@@ -87,16 +83,20 @@ static double* CNum4SimDiff_doHeunMethod(int n, double *yi, double h, Func func)
|
|
87
83
|
}
|
88
84
|
return yi_1;
|
89
85
|
}
|
90
|
-
static double* CNum4SimDiff_doRungeKuttaMethod(int n, double *yi, double h,
|
86
|
+
static double* CNum4SimDiff_doRungeKuttaMethod(int n, double *yi, double h, double *f)
|
91
87
|
{
|
92
88
|
int i;
|
93
|
-
double *f = func(n, yi);
|
94
89
|
double *yi_1 = malloc(sizeof(double) * n);
|
95
90
|
double *k1 = malloc(sizeof(double) * n);
|
96
91
|
double *k2 = malloc(sizeof(double) * n);
|
97
92
|
double *k3 = malloc(sizeof(double) * n);
|
98
93
|
double *k4 = malloc(sizeof(double) * n);
|
99
94
|
|
95
|
+
assert(yi_1 != 0);
|
96
|
+
assert(k1 != 0);
|
97
|
+
assert(k2 != 0);
|
98
|
+
assert(k3 != 0);
|
99
|
+
assert(k4 != 0);
|
100
100
|
// k1 = h * f(xi, y)
|
101
101
|
// k2 = h * f(xi + h / 2, yi + k1 / 2)
|
102
102
|
// k3 = h * f(xi + h / 2, y1 + k2 / 2)
|
@@ -5,14 +5,12 @@
|
|
5
5
|
/* 構造体宣言 */
|
6
6
|
/**************************************/
|
7
7
|
typedef struct _CNum4SimDiff CNum4SimDiff;
|
8
|
-
typedef double* (*Func)(int n, double* yi);
|
9
8
|
|
10
9
|
struct _CNum4SimDiff
|
11
10
|
{
|
12
|
-
double* (*
|
13
|
-
double* (*
|
14
|
-
double* (*
|
15
|
-
double* (*FP_rungeKuttaMethod)(int n, double *yi, double h, Func func);
|
11
|
+
double* (*FP_eulerMethod)(int n, double *yi, double h, double *f);
|
12
|
+
double* (*FP_heunMethod)(int n, double *yi, double h, double *f);
|
13
|
+
double* (*FP_rungeKuttaMethod)(int n, double *yi, double h, double *f);
|
16
14
|
};
|
17
15
|
/**************************************/
|
18
16
|
/* define宣言 */
|
@@ -20,8 +18,7 @@ struct _CNum4SimDiff
|
|
20
18
|
/**************************************/
|
21
19
|
/* プロトタイプ宣言 */
|
22
20
|
/**************************************/
|
23
|
-
double*
|
24
|
-
double*
|
25
|
-
double*
|
26
|
-
double* CNum4SimDiff_rungeKuttaMethod(int n, double *yi, double h, Func func);
|
21
|
+
double* CNum4SimDiff_eulerMethod(int n, double *yi, double h, double *f);
|
22
|
+
double* CNum4SimDiff_heunMethod(int n, double *yi, double h, double *f);
|
23
|
+
double* CNum4SimDiff_rungeKuttaMethod(int n, double *yi, double h, double *f);
|
27
24
|
#endif
|
data/lib/num4simdiff.rb
CHANGED
@@ -6,31 +6,13 @@ module Num4SimDiffLib
|
|
6
6
|
extend FFI::Library
|
7
7
|
|
8
8
|
ffi_lib FFI::Compiler::Loader.find('num4simdiff')
|
9
|
-
|
10
|
-
# @overload f(n, yn)
|
11
|
-
# dy = f(n, yn)
|
12
|
-
# @yield [n, yn] dy = f(n, yn)
|
13
|
-
# @yieldparam [int] n ynの個数
|
14
|
-
# @yieldparam [pointer] yn FFI::Pointer
|
15
|
-
# @return [pointer] xiに対するyの値(FFI::Pointer)
|
16
|
-
callback :f, [:int, :pointer], :pointer
|
17
|
-
|
18
|
-
attach_function :dmyFFI,
|
19
|
-
:CNum4SimDiff_dmy, [:int, :buffer_in, :double, :f], :pointer
|
20
9
|
attach_function :eulerMethodFFI,
|
21
|
-
:CNum4SimDiff_eulerMethod, [:int, :buffer_in, :double, :
|
10
|
+
:CNum4SimDiff_eulerMethod, [:int, :buffer_in, :double, :buffer_in], :pointer
|
22
11
|
attach_function :heunMethodFFI,
|
23
|
-
:CNum4SimDiff_heunMethod, [:int, :buffer_in, :double, :
|
12
|
+
:CNum4SimDiff_heunMethod, [:int, :buffer_in, :double, :buffer_in], :pointer
|
24
13
|
attach_function :rungeKuttaMethodFFI,
|
25
|
-
:CNum4SimDiff_rungeKuttaMethod, [:int, :buffer_in, :double, :
|
14
|
+
:CNum4SimDiff_rungeKuttaMethod, [:int, :buffer_in, :double, :buffer_in], :pointer
|
26
15
|
class << self
|
27
|
-
# @private
|
28
|
-
def dmy(yi, h, func)
|
29
|
-
n = yi.size
|
30
|
-
yi_ptr = cnvRbAry2pt(n, yi)
|
31
|
-
yi_1_ptr = dmyFFI(n, yi_ptr, h, func)
|
32
|
-
yi_1 = cnvPt2RbAry(n, yi_1_ptr)
|
33
|
-
end
|
34
16
|
#
|
35
17
|
# オイラー法による数値計算
|
36
18
|
# @overload eulerMethod(yi, h, func)
|
@@ -39,12 +21,24 @@ module Num4SimDiffLib
|
|
39
21
|
# @param [double] h 刻み幅
|
40
22
|
# @param [callback] func xiに対する傾きを計算する関数
|
41
23
|
# @return [double[]] xi+hに対するyi_1の値(配列)
|
24
|
+
# @example
|
25
|
+
# func = Proc.new do | n, yi |
|
26
|
+
# f = []
|
27
|
+
# f[0] = yi[0]
|
28
|
+
# f[1] = yi[1]
|
29
|
+
# next f
|
30
|
+
# end
|
31
|
+
# yi = [1.0, 1.0]
|
32
|
+
# yi_1 = Num4SimDiffLib.eulerMethod(yi, 0.001, func)
|
42
33
|
#
|
43
34
|
def eulerMethod(yi, h, func)
|
44
35
|
n = yi.size
|
36
|
+
f = func.call(n, yi)
|
37
|
+
f_ptr = cnvRbAry2pt(n, f)
|
45
38
|
yi_ptr = cnvRbAry2pt(n, yi)
|
46
|
-
yi_1_ptr = eulerMethodFFI(n, yi_ptr, h,
|
39
|
+
yi_1_ptr = eulerMethodFFI(n, yi_ptr, h, f_ptr)
|
47
40
|
yi_1 = cnvPt2RbAry(n, yi_1_ptr)
|
41
|
+
f_ptr.free()
|
48
42
|
return yi_1
|
49
43
|
end
|
50
44
|
#
|
@@ -55,12 +49,24 @@ module Num4SimDiffLib
|
|
55
49
|
# @param [double] h 刻み幅
|
56
50
|
# @param [callback] func xiに対する傾きを計算する関数
|
57
51
|
# @return [double[]] xi+hに対するyi_1の値(配列)
|
52
|
+
# @example
|
53
|
+
# func = Proc.new do | n, yi |
|
54
|
+
# f = []
|
55
|
+
# f[0] = yi[0]
|
56
|
+
# f[1] = yi[1]
|
57
|
+
# next f
|
58
|
+
# end
|
59
|
+
# yi = [1.0, 1.0]
|
60
|
+
# yi_1 = Num4SimDiffLib.heunMethod(yi, 0.001, func)
|
58
61
|
#
|
59
62
|
def heunMethod(yi, h, func)
|
60
63
|
n = yi.size
|
64
|
+
f = func.call(n, yi)
|
65
|
+
f_ptr = cnvRbAry2pt(n, f)
|
61
66
|
yi_ptr = cnvRbAry2pt(n, yi)
|
62
|
-
yi_1_ptr = heunMethodFFI(n, yi_ptr, h,
|
67
|
+
yi_1_ptr = heunMethodFFI(n, yi_ptr, h, f_ptr)
|
63
68
|
yi_1 = cnvPt2RbAry(n, yi_1_ptr)
|
69
|
+
f_ptr.free()
|
64
70
|
return yi_1
|
65
71
|
end
|
66
72
|
#
|
@@ -71,21 +77,29 @@ module Num4SimDiffLib
|
|
71
77
|
# @param [double] h 刻み幅
|
72
78
|
# @param [callback] func xiに対する傾きを計算する関数
|
73
79
|
# @return [double[]] xi+hに対するyi_1の値(配列)
|
80
|
+
# @example
|
81
|
+
# func = Proc.new do | n, yi |
|
82
|
+
# f = []
|
83
|
+
# f[0] = yi[0]
|
84
|
+
# f[1] = yi[1]
|
85
|
+
# next f
|
86
|
+
# end
|
87
|
+
# yi = [1.0, 1.0]
|
88
|
+
# yi_1 = Num4SimDiffLib.rungeKuttaMethod(yi, 0.001, func)
|
74
89
|
#
|
75
90
|
def rungeKuttaMethod(yi, h, func)
|
76
91
|
n = yi.size
|
92
|
+
f = func.call(n, yi)
|
93
|
+
f_ptr = cnvRbAry2pt(n, f)
|
77
94
|
yi_ptr = cnvRbAry2pt(n, yi)
|
78
|
-
yi_1_ptr = rungeKuttaMethodFFI(n, yi_ptr, h,
|
95
|
+
yi_1_ptr = rungeKuttaMethodFFI(n, yi_ptr, h, f_ptr)
|
79
96
|
yi_1 = cnvPt2RbAry(n, yi_1_ptr)
|
97
|
+
f_ptr.free()
|
80
98
|
return yi_1
|
81
99
|
end
|
82
100
|
|
83
101
|
#
|
84
|
-
#
|
85
|
-
# @overload cnvRbAry2pt(n, ary)
|
86
|
-
# @param [int] n 配列の個数
|
87
|
-
# @param [double[]] ary yiの値(配列)
|
88
|
-
# @return [pointer] FFI::Pointer
|
102
|
+
# @private
|
89
103
|
def cnvRbAry2pt(n, ary)
|
90
104
|
yi_ptr = FFI::MemoryPointer.new(:double, n)
|
91
105
|
n.times.map { |i|
|
@@ -94,17 +108,15 @@ module Num4SimDiffLib
|
|
94
108
|
return yi_ptr
|
95
109
|
end
|
96
110
|
#
|
97
|
-
#
|
98
|
-
# @overload cnvPt2RbAry(n, pt)
|
99
|
-
# @param [int] n 配列の個数
|
100
|
-
# @param [pointer] pt FFI::Pointer
|
101
|
-
# @return [double[]] yiの値(配列)
|
111
|
+
# @private
|
102
112
|
def cnvPt2RbAry(n, pt)
|
103
113
|
rbAry = n.times.map { |i|
|
104
114
|
pt.get_double(i * Fiddle::SIZEOF_DOUBLE)
|
105
115
|
}
|
106
116
|
return rbAry
|
107
117
|
end
|
118
|
+
private :cnvRbAry2pt
|
119
|
+
private :cnvPt2RbAry
|
108
120
|
private :eulerMethodFFI
|
109
121
|
private :heunMethodFFI
|
110
122
|
private :rungeKuttaMethodFFI
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: num4simdiff
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- siranovel
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-05-
|
11
|
+
date: 2023-05-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ffi-compiler
|
@@ -70,8 +70,9 @@ licenses:
|
|
70
70
|
- MIT
|
71
71
|
metadata:
|
72
72
|
changelog_uri: http://github.com/siranovel/num4simdiffrent/blob/main/CHANGELOG.md
|
73
|
-
documentation_uri: https://rubydoc.info/gems/num4simdiff/0.
|
73
|
+
documentation_uri: https://rubydoc.info/gems/num4simdiff/0.2.1
|
74
74
|
homepage_uri: http://github.com/siranovel/num4simdiffrent
|
75
|
+
wiki_uri: https://github.com/siranovel/mydocs/tree/main/num4simdiff
|
75
76
|
post_install_message:
|
76
77
|
rdoc_options:
|
77
78
|
- "--no-private"
|