nmatrix 0.0.9 → 0.1.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (101) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +1 -0
  3. data/History.txt +95 -1
  4. data/LICENSE.txt +2 -2
  5. data/README.rdoc +24 -26
  6. data/Rakefile +32 -16
  7. data/ext/nmatrix/data/complex.h +2 -2
  8. data/ext/nmatrix/data/data.cpp +27 -51
  9. data/ext/nmatrix/data/data.h +92 -4
  10. data/ext/nmatrix/data/meta.h +2 -2
  11. data/ext/nmatrix/data/rational.h +2 -2
  12. data/ext/nmatrix/data/ruby_object.h +2 -2
  13. data/ext/nmatrix/extconf.rb +87 -86
  14. data/ext/nmatrix/math.cpp +45 -40
  15. data/ext/nmatrix/math/asum.h +3 -3
  16. data/ext/nmatrix/math/geev.h +2 -2
  17. data/ext/nmatrix/math/gemm.h +6 -2
  18. data/ext/nmatrix/math/gemv.h +6 -2
  19. data/ext/nmatrix/math/ger.h +2 -2
  20. data/ext/nmatrix/math/gesdd.h +2 -2
  21. data/ext/nmatrix/math/gesvd.h +2 -2
  22. data/ext/nmatrix/math/getf2.h +2 -2
  23. data/ext/nmatrix/math/getrf.h +2 -2
  24. data/ext/nmatrix/math/getri.h +2 -2
  25. data/ext/nmatrix/math/getrs.h +7 -3
  26. data/ext/nmatrix/math/idamax.h +2 -2
  27. data/ext/nmatrix/math/inc.h +12 -6
  28. data/ext/nmatrix/math/laswp.h +2 -2
  29. data/ext/nmatrix/math/long_dtype.h +2 -2
  30. data/ext/nmatrix/math/math.h +16 -10
  31. data/ext/nmatrix/math/nrm2.h +3 -3
  32. data/ext/nmatrix/math/potrs.h +7 -3
  33. data/ext/nmatrix/math/rot.h +2 -2
  34. data/ext/nmatrix/math/rotg.h +2 -2
  35. data/ext/nmatrix/math/scal.h +2 -2
  36. data/ext/nmatrix/math/swap.h +2 -2
  37. data/ext/nmatrix/math/trsm.h +7 -3
  38. data/ext/nmatrix/nm_memory.h +60 -0
  39. data/ext/nmatrix/nmatrix.cpp +13 -47
  40. data/ext/nmatrix/nmatrix.h +37 -12
  41. data/ext/nmatrix/ruby_constants.cpp +4 -2
  42. data/ext/nmatrix/ruby_constants.h +4 -2
  43. data/ext/nmatrix/ruby_nmatrix.c +937 -170
  44. data/ext/nmatrix/storage/common.cpp +2 -2
  45. data/ext/nmatrix/storage/common.h +2 -2
  46. data/ext/nmatrix/storage/{dense.cpp → dense/dense.cpp} +253 -100
  47. data/ext/nmatrix/storage/{dense.h → dense/dense.h} +6 -5
  48. data/ext/nmatrix/storage/{list.cpp → list/list.cpp} +517 -98
  49. data/ext/nmatrix/storage/{list.h → list/list.h} +13 -6
  50. data/ext/nmatrix/storage/storage.cpp +48 -19
  51. data/ext/nmatrix/storage/storage.h +4 -4
  52. data/ext/nmatrix/storage/yale/class.h +112 -43
  53. data/ext/nmatrix/storage/yale/iterators/base.h +2 -2
  54. data/ext/nmatrix/storage/yale/iterators/iterator.h +2 -2
  55. data/ext/nmatrix/storage/yale/iterators/row.h +2 -2
  56. data/ext/nmatrix/storage/yale/iterators/row_stored.h +2 -2
  57. data/ext/nmatrix/storage/yale/iterators/row_stored_nd.h +4 -3
  58. data/ext/nmatrix/storage/yale/iterators/stored_diagonal.h +2 -2
  59. data/ext/nmatrix/storage/yale/math/transpose.h +2 -2
  60. data/ext/nmatrix/storage/yale/yale.cpp +343 -52
  61. data/ext/nmatrix/storage/yale/yale.h +7 -3
  62. data/ext/nmatrix/types.h +2 -2
  63. data/ext/nmatrix/util/io.cpp +5 -5
  64. data/ext/nmatrix/util/io.h +2 -2
  65. data/ext/nmatrix/util/sl_list.cpp +40 -27
  66. data/ext/nmatrix/util/sl_list.h +3 -3
  67. data/ext/nmatrix/util/util.h +2 -2
  68. data/lib/nmatrix.rb +2 -2
  69. data/lib/nmatrix/blas.rb +2 -2
  70. data/lib/nmatrix/enumerate.rb +17 -6
  71. data/lib/nmatrix/io/market.rb +2 -3
  72. data/lib/nmatrix/io/mat5_reader.rb +2 -2
  73. data/lib/nmatrix/io/mat_reader.rb +2 -2
  74. data/lib/nmatrix/lapack.rb +46 -46
  75. data/lib/nmatrix/math.rb +213 -20
  76. data/lib/nmatrix/monkeys.rb +24 -2
  77. data/lib/nmatrix/nmatrix.rb +394 -9
  78. data/lib/nmatrix/nvector.rb +2 -64
  79. data/lib/nmatrix/rspec.rb +2 -2
  80. data/lib/nmatrix/shortcuts.rb +14 -61
  81. data/lib/nmatrix/version.rb +11 -3
  82. data/lib/nmatrix/yale_functions.rb +4 -4
  83. data/nmatrix.gemspec +2 -7
  84. data/scripts/mac-brew-gcc.sh +11 -8
  85. data/scripts/mac-mavericks-brew-gcc.sh +22 -0
  86. data/spec/00_nmatrix_spec.rb +116 -7
  87. data/spec/01_enum_spec.rb +17 -3
  88. data/spec/02_slice_spec.rb +11 -3
  89. data/spec/blas_spec.rb +5 -2
  90. data/spec/elementwise_spec.rb +5 -2
  91. data/spec/io_spec.rb +27 -17
  92. data/spec/lapack_spec.rb +157 -9
  93. data/spec/math_spec.rb +95 -4
  94. data/spec/nmatrix_yale_spec.rb +21 -26
  95. data/spec/rspec_monkeys.rb +27 -0
  96. data/spec/rspec_spec.rb +2 -2
  97. data/spec/shortcuts_spec.rb +5 -10
  98. data/spec/slice_set_spec.rb +6 -2
  99. data/spec/spec_helper.rb +3 -2
  100. data/spec/stat_spec.rb +174 -158
  101. metadata +15 -15
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
@@ -89,7 +89,11 @@ extern "C" {
89
89
  void nm_yale_storage_delete_ref(STORAGE* s);
90
90
  void nm_yale_storage_init(YALE_STORAGE* s, void* default_val);
91
91
  void nm_yale_storage_mark(STORAGE*);
92
-
92
+ void nm_yale_storage_register(const STORAGE* s);
93
+ void nm_yale_storage_unregister(const STORAGE* s);
94
+ void nm_yale_storage_register_a(void* a, size_t size);
95
+ void nm_yale_storage_unregister_a(void* a, size_t size);
96
+
93
97
  ///////////////
94
98
  // Accessors //
95
99
  ///////////////
data/ext/nmatrix/types.h CHANGED
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
@@ -75,7 +75,7 @@ template <typename DType, typename MDType>
75
75
  char* matlab_cstring_to_dtype_string(size_t& result_len, const char* str, size_t bytes) {
76
76
 
77
77
  result_len = sizeof(DType) * bytes / sizeof(MDType);
78
- char* result = ALLOC_N(char, result_len);
78
+ char* result = NM_ALLOC_N(char, result_len);
79
79
 
80
80
  if (bytes % sizeof(MDType) != 0) {
81
81
  rb_raise(rb_eArgError, "the given string does not divide evenly for the given MATLAB dtype");
@@ -223,7 +223,7 @@ static VALUE nm_rbstring_matlab_repack(VALUE self, VALUE str, VALUE from, VALUE
223
223
 
224
224
  // Encode as 8-bit ASCII with a length -- don't want to hiccup on \0
225
225
  VALUE result = rb_str_new(repacked_data, repacked_data_length);
226
- xfree(repacked_data); // Don't forget to free what we allocated!
226
+ NM_FREE(repacked_data); // Don't forget to free what we allocated!
227
227
 
228
228
  return result;
229
229
  }
@@ -246,7 +246,7 @@ static VALUE nm_rbstring_merge(VALUE self, VALUE rb_real, VALUE rb_imaginary, VA
246
246
  char *real = RSTRING_PTR(rb_real),
247
247
  *imag = RSTRING_PTR(rb_imaginary);
248
248
 
249
- char* merge = ALLOCA_N(char, RSTRING_LEN(rb_real)*2);
249
+ char* merge = NM_ALLOCA_N(char, RSTRING_LEN(rb_real)*2);
250
250
 
251
251
  size_t merge_pos = 0;
252
252
 
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
@@ -1,6 +1,16 @@
1
+ /////////////////////////////////////////////////////////////////////
2
+ // = NMatrix
1
3
  //
2
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
3
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
4
+ // A linear algebra library for scientific computation in Ruby.
5
+ // NMatrix is part of SciRuby.
6
+ //
7
+ // NMatrix was originally inspired by and derived from NArray, by
8
+ // Masahiro Tanaka: http://narray.rubyforge.org
9
+ //
10
+ // == Copyright Information
11
+ //
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
4
14
  //
5
15
  // Please see LICENSE.txt for additional copyright notices.
6
16
  //
@@ -31,6 +41,8 @@
31
41
 
32
42
  #include "sl_list.h"
33
43
 
44
+ #include "storage/list/list.h"
45
+
34
46
  namespace nm { namespace list {
35
47
 
36
48
  /*
@@ -58,7 +70,7 @@ namespace nm { namespace list {
58
70
  * Creates an empty linked list.
59
71
  */
60
72
  LIST* create(void) {
61
- LIST* list = ALLOC( LIST );
73
+ LIST* list = NM_ALLOC( LIST );
62
74
  list->first = NULL;
63
75
  return list;
64
76
  }
@@ -77,18 +89,19 @@ void del(LIST* list, size_t recursions) {
77
89
 
78
90
  if (recursions == 0) {
79
91
  //fprintf(stderr, " free_val: %p\n", curr->val);
80
- xfree(curr->val);
92
+ nm_list_storage_completely_unregister_node(curr);
93
+ NM_FREE(curr->val);
81
94
 
82
95
  } else {
83
96
  //fprintf(stderr, " free_list: %p\n", list);
84
97
  del((LIST*)curr->val, recursions - 1);
85
98
  }
86
99
 
87
- xfree(curr);
100
+ NM_FREE(curr);
88
101
  curr = next;
89
102
  }
90
103
  //fprintf(stderr, " free_list: %p\n", list);
91
- xfree(list);
104
+ NM_FREE(list);
92
105
  }
93
106
 
94
107
  /*
@@ -122,10 +135,10 @@ void mark(LIST* list, size_t recursions) {
122
135
  * checks, just inserts.
123
136
  */
124
137
  NODE* insert_first_node(LIST* list, size_t key, void* val, size_t val_size) {
125
- NODE* ins = ALLOC(NODE);
138
+ NODE* ins = NM_ALLOC(NODE);
126
139
  ins->next = list->first;
127
140
 
128
- void* val_copy = ALLOC_N(char, val_size);
141
+ void* val_copy = NM_ALLOC_N(char, val_size);
129
142
  memcpy(val_copy, val, val_size);
130
143
 
131
144
  ins->val = reinterpret_cast<void*>(val_copy);
@@ -136,7 +149,7 @@ NODE* insert_first_node(LIST* list, size_t key, void* val, size_t val_size) {
136
149
  }
137
150
 
138
151
  NODE* insert_first_list(LIST* list, size_t key, LIST* l) {
139
- NODE* ins = ALLOC(NODE);
152
+ NODE* ins = NM_ALLOC(NODE);
140
153
  ins->next = list->first;
141
154
 
142
155
  ins->val = reinterpret_cast<void*>(l);
@@ -160,7 +173,7 @@ NODE* insert(LIST* list, bool replace, size_t key, void* val) {
160
173
  // List is empty
161
174
 
162
175
  //if (!(ins = malloc(sizeof(NODE)))) return NULL;
163
- ins = ALLOC(NODE);
176
+ ins = NM_ALLOC(NODE);
164
177
  ins->next = NULL;
165
178
  ins->val = val;
166
179
  ins->key = key;
@@ -172,7 +185,7 @@ NODE* insert(LIST* list, bool replace, size_t key, void* val) {
172
185
  // Goes at the beginning of the list
173
186
 
174
187
  //if (!(ins = malloc(sizeof(NODE)))) return NULL;
175
- ins = ALLOC(NODE);
188
+ ins = NM_ALLOC(NODE);
176
189
  ins->next = list->first;
177
190
  ins->val = val;
178
191
  ins->key = key;
@@ -187,11 +200,11 @@ NODE* insert(LIST* list, bool replace, size_t key, void* val) {
187
200
  if (ins->key == key) {
188
201
  // key already exists
189
202
  if (replace) {
190
- xfree(ins->val);
203
+ nm_list_storage_completely_unregister_node(ins);
204
+ NM_FREE(ins->val);
191
205
  ins->val = val;
192
-
193
206
  } else {
194
- xfree(val);
207
+ NM_FREE(val);
195
208
  }
196
209
 
197
210
  return ins;
@@ -208,7 +221,7 @@ NODE* insert(LIST* list, bool replace, size_t key, void* val) {
208
221
  */
209
222
  NODE* insert_after(NODE* node, size_t key, void* val) {
210
223
  //if (!(ins = malloc(sizeof(NODE)))) return NULL;
211
- NODE* ins = ALLOC(NODE);
224
+ NODE* ins = NM_ALLOC(NODE);
212
225
 
213
226
  // insert 'ins' between 'node' and 'node->next'
214
227
  ins->next = node->next;
@@ -231,7 +244,7 @@ NODE* replace_insert_after(NODE* node, size_t key, void* val, bool copy, size_t
231
244
  // Should we copy into the current one or free and insert?
232
245
  if (copy) memcpy(node->next->val, val, copy_size);
233
246
  else {
234
- xfree(node->next->val);
247
+ NM_FREE(node->next->val);
235
248
  node->next->val = val;
236
249
  }
237
250
 
@@ -240,7 +253,7 @@ NODE* replace_insert_after(NODE* node, size_t key, void* val, bool copy, size_t
240
253
  } else { // no next node, or if there is one, it's greater than the current key
241
254
 
242
255
  if (copy) {
243
- void* val_copy = ALLOC_N(char, copy_size);
256
+ void* val_copy = NM_ALLOC_N(char, copy_size);
244
257
  memcpy(val_copy, val, copy_size);
245
258
  return insert_after(node, key, val_copy);
246
259
  } else {
@@ -256,7 +269,7 @@ NODE* replace_insert_after(NODE* node, size_t key, void* val, bool copy, size_t
256
269
  * Functions analogously to list::insert but this inserts a copy of the value instead of the original.
257
270
  */
258
271
  NODE* insert_copy(LIST *list, bool replace, size_t key, void *val, size_t size) {
259
- void *copy_val = ALLOC_N(char, size);
272
+ void *copy_val = NM_ALLOC_N(char, size);
260
273
  memcpy(copy_val, val, size);
261
274
 
262
275
  return insert(list, replace, key, copy_val);
@@ -272,7 +285,7 @@ void* remove_by_node(LIST* list, NODE* prev, NODE* rm) {
272
285
  else prev->next = rm->next;
273
286
 
274
287
  void* val = rm->val;
275
- xfree(rm);
288
+ NM_FREE(rm);
276
289
 
277
290
  return val;
278
291
  }
@@ -296,7 +309,7 @@ void* remove_by_key(LIST* list, size_t key) {
296
309
  rm = list->first;
297
310
 
298
311
  list->first = rm->next;
299
- xfree(rm);
312
+ NM_FREE(rm);
300
313
 
301
314
  return val;
302
315
  }
@@ -313,7 +326,7 @@ void* remove_by_key(LIST* list, size_t key) {
313
326
 
314
327
  // get the value and free the memory for the node
315
328
  val = rm->val;
316
- xfree(rm);
329
+ NM_FREE(rm);
317
330
 
318
331
  return val;
319
332
  }
@@ -348,7 +361,7 @@ bool remove_recursive(LIST* list, const size_t* coords, const size_t* offsets, c
348
361
 
349
362
  if (remove_parent) { // now empty -- so remove the sub-list
350
363
  // std::cerr << r << ": removing parent list at " << n->key << std::endl;
351
- xfree(remove_by_node(list, prev, n));
364
+ NM_FREE(remove_by_node(list, prev, n));
352
365
 
353
366
  if (prev) n = prev->next && node_is_within_slice(prev->next, coords[r] + offsets[r], lengths[r]) ? prev->next : NULL;
354
367
  else n = node_is_within_slice(list->first, coords[r] + offsets[r], lengths[r]) ? list->first : NULL;
@@ -367,7 +380,7 @@ bool remove_recursive(LIST* list, const size_t* coords, const size_t* offsets, c
367
380
 
368
381
  while (n) {
369
382
  // std::cerr << r << ": removing node at " << n->key << std::endl;
370
- xfree(remove_by_node(list, prev, n));
383
+ NM_FREE(remove_by_node(list, prev, n));
371
384
 
372
385
  if (prev) n = prev->next && node_is_within_slice(prev->next, coords[r] + offsets[r], lengths[r]) ? prev->next : NULL;
373
386
  else n = node_is_within_slice(list->first, coords[r] + offsets[r], lengths[r]) ? list->first : NULL;
@@ -505,7 +518,7 @@ void cast_copy_contents(LIST* lhs, const LIST* rhs, size_t recursions) {
505
518
  if (rhs->first) {
506
519
  // copy head node
507
520
  rcurr = rhs->first;
508
- lcurr = lhs->first = ALLOC( NODE );
521
+ lcurr = lhs->first = NM_ALLOC( NODE );
509
522
 
510
523
  while (rcurr) {
511
524
  lcurr->key = rcurr->key;
@@ -513,14 +526,14 @@ void cast_copy_contents(LIST* lhs, const LIST* rhs, size_t recursions) {
513
526
  if (recursions == 0) {
514
527
  // contents is some kind of value
515
528
 
516
- lcurr->val = ALLOC( LDType );
529
+ lcurr->val = NM_ALLOC( LDType );
517
530
 
518
531
  *reinterpret_cast<LDType*>(lcurr->val) = *reinterpret_cast<RDType*>( rcurr->val );
519
532
 
520
533
  } else {
521
534
  // contents is a list
522
535
 
523
- lcurr->val = ALLOC( LIST );
536
+ lcurr->val = NM_ALLOC( LIST );
524
537
 
525
538
  cast_copy_contents<LDType, RDType>(
526
539
  reinterpret_cast<LIST*>(lcurr->val),
@@ -530,7 +543,7 @@ void cast_copy_contents(LIST* lhs, const LIST* rhs, size_t recursions) {
530
543
  }
531
544
 
532
545
  if (rcurr->next) {
533
- lcurr->next = ALLOC( NODE );
546
+ lcurr->next = NM_ALLOC( NODE );
534
547
 
535
548
  } else {
536
549
  lcurr->next = NULL;
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
@@ -90,7 +90,7 @@ bool node_is_within_slice(NODE* n, size_t coord, size_t len);
90
90
 
91
91
  template <typename Type>
92
92
  inline NODE* insert_helper(LIST* list, NODE* node, size_t key, Type val) {
93
- Type* val_mem = ALLOC(Type);
93
+ Type* val_mem = NM_ALLOC(Type);
94
94
  *val_mem = val;
95
95
 
96
96
  if (node == NULL) {
@@ -9,8 +9,8 @@
9
9
  //
10
10
  // == Copyright Information
11
11
  //
12
- // SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- // NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ // SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ // NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  //
15
15
  // Please see LICENSE.txt for additional copyright notices.
16
16
  //
data/lib/nmatrix.rb CHANGED
@@ -8,8 +8,8 @@
8
8
  #
9
9
  # == Copyright Information
10
10
  #
11
- # SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
12
- # NMatrix is Copyright (c) 2013, Ruby Science Foundation
11
+ # SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
12
+ # NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
13
13
  #
14
14
  # Please see LICENSE.txt for additional copyright notices.
15
15
  #
data/lib/nmatrix/blas.rb CHANGED
@@ -9,8 +9,8 @@
9
9
  #
10
10
  # == Copyright Information
11
11
  #
12
- # SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- # NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ # SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ # NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  #
15
15
  # Please see LICENSE.txt for additional copyright notices.
16
16
  #
@@ -9,8 +9,8 @@
9
9
  #
10
10
  # == Copyright Information
11
11
  #
12
- # SciRuby is Copyright (c) 2010 - 2013, Ruby Science Foundation
13
- # NMatrix is Copyright (c) 2013, Ruby Science Foundation
12
+ # SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ # NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  #
15
15
  # Please see LICENSE.txt for additional copyright notices.
16
16
  #
@@ -66,9 +66,12 @@ class NMatrix
66
66
  #
67
67
  # Returns an NMatrix if a block is given. For an Array, use #flat_map
68
68
  #
69
+ # Note that #map will always return an :object matrix, because it has no way of knowing
70
+ # how to handle operations on the different dtypes.
71
+ #
69
72
  def map(&bl)
70
73
  return enum_for(:map) unless block_given?
71
- cp = self.dup
74
+ cp = self.cast(dtype: :object)
72
75
  cp.map! &bl
73
76
  cp
74
77
  end
@@ -83,10 +86,18 @@ class NMatrix
83
86
  #
84
87
  def map!
85
88
  return enum_for(:map!) unless block_given?
89
+ iterated = false
86
90
  self.each_stored_with_indices do |e, *i|
91
+ iterated = true
87
92
  self[*i] = (yield e)
88
93
  end
89
- self
94
+ #HACK: if there's a single element in a non-dense matrix, it won't iterate and
95
+ #won't change the default value; this ensures that it does get changed.
96
+ unless iterated then
97
+ self.each_with_indices do |e, *i|
98
+ self[*i] = (yield e)
99
+ end
100
+ end
90
101
  end
91
102
 
92
103
 
@@ -215,7 +226,7 @@ class NMatrix
215
226
  first_as_acc = false
216
227
 
217
228
  if initial then
218
- acc = NMatrix.new(new_shape, initial, :dtype => dtype || self.dtype)
229
+ acc = NMatrix.new(new_shape, initial, :dtype => dtype || self.dtype, stype: self.stype)
219
230
  else
220
231
  each_rank(dimen) do |sub_mat|
221
232
  acc = (sub_mat.is_a?(NMatrix) and !dtype.nil? and dtype != self.dtype) ? sub_mat.cast(self.stype, dtype) : sub_mat
@@ -238,4 +249,4 @@ class NMatrix
238
249
  alias :reduce_along_dim :inject_rank
239
250
  alias :inject_along_dim :inject_rank
240
251
 
241
- end
252
+ end
@@ -1,4 +1,3 @@
1
- #--
2
1
  # = NMatrix
3
2
  #
4
3
  # A linear algebra library for scientific computation in Ruby.
@@ -9,8 +8,8 @@
9
8
  #
10
9
  # == Copyright Information
11
10
  #
12
- # SciRuby is Copyright (c) 2010 - 2012, Ruby Science Foundation
13
- # NMatrix is Copyright (c) 2012, Ruby Science Foundation
11
+ # SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
12
+ # NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
13
  #
15
14
  # Please see LICENSE.txt for additional copyright notices.
16
15
  #
@@ -9,8 +9,8 @@
9
9
  #
10
10
  # == Copyright Information
11
11
  #
12
- # SciRuby is Copyright (c) 2010 - 2012, Ruby Science Foundation
13
- # NMatrix is Copyright (c) 2012, Ruby Science Foundation
12
+ # SciRuby is Copyright (c) 2010 - 2014, Ruby Science Foundation
13
+ # NMatrix is Copyright (c) 2012 - 2014, John Woods and the Ruby Science Foundation
14
14
  #
15
15
  # Please see LICENSE.txt for additional copyright notices.
16
16
  #