supplement 2.26 → 2.29

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6a901ea1ffc61c2fc508aa25ecded2cdf4668547f9dccdfa9b8cfbe7e8aea505
4
- data.tar.gz: b156a06a97b495b524550fc903de39a7db9f007451aa6102ac50e66391a304a5
3
+ metadata.gz: 9d98b193bc4d1cc8ede4e690103285660b92acbef10bc2c8c9fbe9774968b55e
4
+ data.tar.gz: ce38aef42ac4a5aceb953eee5090d62b09da647c6badd39eb13fcf6ae75124d7
5
5
  SHA512:
6
- metadata.gz: 197c7244e880680e7e9623236dc2e81bfa76f54df5708c75a73d9fd839f40bcd835b2a3e99e89e99ffbffa54386ef0c09de421e6b761937860dd8047119f58c9
7
- data.tar.gz: a73e89d0257c48cd54916446ec507ed431e01451bb52cc29d6b50e65517b18b02c8aebd351d924c8f95588d15af8cc3e1ca4349504540150f40a922cb0a1c1f0
6
+ metadata.gz: c8a1ca6542111abec4919e6b0fafbc665e88baf3de003ccb696586060b4508f0d8c95c5a85d5b2b2bbab85aad0f2c7132bee0458dd64f799d6825c8f404e6754
7
+ data.tar.gz: 30703341388fdd2895f68879925eef1d4a1e94c22e177470cc7689b5e7a0addd5693bab20969afa8b127e6a137e5794dba323bdf2d1e2824adfe73b813103dc5
data/LICENSE CHANGED
@@ -1,20 +1,24 @@
1
- = supplement Ruby Gem
1
+ # BSD-2-clause license, extended by language use conditions
2
2
 
3
-
4
- Copyright (C) 2009-2024, Bertram Scharpf <software@bertram-scharpf.de>.
3
+ Copyright (C) 2009-2025, Bertram Scharpf <software@bertram-scharpf.de>.
5
4
  All rights reserved.
6
5
 
7
6
  Redistribution and use in source and binary forms, with or without
8
7
  modification, are permitted provided that the following conditions are
9
8
  met:
10
9
 
11
- * Redistributions of source code must retain the above copyright
12
- notice, this list of conditions and the following disclaimer.
10
+ * Redistributions of source code must retain the above copyright
11
+ notice, this list of conditions and the following disclaimer.
12
+
13
+ * Redistributions in binary form must reproduce the above copyright
14
+ notice, this list of conditions and the following disclaimer in
15
+ the documentation and/or other materials provided with the
16
+ distribution.
13
17
 
14
- * Redistributions in binary form must reproduce the above copyright
15
- notice, this list of conditions and the following disclaimer in
16
- the documentation and/or other materials provided with the
17
- distribution.
18
+ * Redistributions must not contain any clauses about anticipated
19
+ harassment or discrimination, nor must they be held in a so-called
20
+ "inclusive language". As far as German language is used, the
21
+ conditions mentioned below additionally apply.
18
22
 
19
23
  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
20
24
  IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
@@ -28,3 +32,21 @@ LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
28
32
  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
29
33
  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
34
 
35
+
36
+ ## Use of the German Language
37
+
38
+ Beim Gebrauch deutscher Sprache sind Weiterentwicklungen und
39
+ -verbreitungen nur gestattet unter Einhaltung sowie abermaligen
40
+ Einforderns folgender zusätzlicher Bedingungen:
41
+
42
+ * Keine Verwendung von sogenannter „geschlechtergerechter Sprache“,
43
+ also Anfügen von weiblichen Endungen mit Binnen-I, Sternchen,
44
+ Doppelpunkt, Unterstrich oder ähnlichem, oder Konstruktionen, die
45
+ den Sachverhalt falsch wiedergeben („Radfahrende“, „Studierende“).
46
+
47
+ * Keine Verwendung der „reformierten Rechtschreibung“ von 1996,
48
+ insbesondere Doppel-S am Silbenende, „plazieren“ mit T, sowie
49
+ Großschreibung von Wendungen wie „des weiteren“.
50
+
51
+
52
+ <!-- vim:set ft=markdown : -->
data/README.md ADDED
@@ -0,0 +1,54 @@
1
+ # supplement 2.29 -- Useful Ruby enhancements
2
+
3
+ Some simple Ruby extensions.
4
+
5
+
6
+ ## Motivation
7
+
8
+ The original motivation was my conviction that a language that has a
9
+ `Numeric#nonzero?` method induces a programming style that as well demands
10
+ for a `String#notempty?` method.
11
+
12
+
13
+ ## Description
14
+
15
+ These are methods on standard classes that didn't manage to become part of
16
+ the Ruby interpreter. (Although, some did in the meantime.)
17
+
18
+ They are all very small, most of them have less than 15 lines of code.
19
+ So they would not be a weight in the Ruby interpreter but it is very
20
+ difficult to convince a majority that they belong there.
21
+
22
+ The methods won't be useful for everybody but some programmers may like
23
+ to make them part of their programming style.
24
+
25
+ If you like to get taunted, then go to the Ruby mailing list and propose
26
+ one of them to be included into the Ruby standard.
27
+
28
+
29
+ ## Contents (uncomplete)
30
+
31
+ * `String#notempty?`
32
+ * `String#head`
33
+ * `String#tail`
34
+ * `String#rest`
35
+ * `String#starts_with?`/`ends_with?`
36
+ * `Array#notempty?`
37
+ * `Array#first=`/`last=`
38
+ * `Hash#notempty?`
39
+ * `Struct.[]`
40
+ * `Integer.roman`
41
+ * `Date.easter`
42
+ * `TCPServer/UNIXServer.accept` with a code block
43
+ * `File system stats`
44
+ * `Process.renice`
45
+ * Interval timer
46
+ * `LockedFile`
47
+
48
+
49
+ ## Copyright
50
+
51
+ * (C) 2009-2025 Bertram Scharpf <software@bertram-scharpf.de>
52
+ * License: [BSD-2-Clause+](./LICENSE)
53
+ * Repository: [ruby-supplement](https://github.com/BertramScharpf/ruby-supplement)
54
+
data/lib/mkrf_conf CHANGED
@@ -11,13 +11,6 @@ Autorake.configure {
11
11
  extending_ruby
12
12
 
13
13
  if RUBY_VERSION < "3.3" then
14
- if RUBY_VERSION < "2.7" then
15
- if RUBY_VERSION < "2.6" then
16
- enable :dir_children
17
- end
18
- else
19
- enable :super_kwargs
20
- end
21
14
  enable :old_io_functions
22
15
  end
23
16
 
@@ -26,10 +19,6 @@ Autorake.configure {
26
19
  have_header "ruby/io.h"
27
20
  have_header "ruby/re.h"
28
21
 
29
- have_function "rb_thread_wait_for"
30
-
31
- have_function "cbrt"
32
-
33
22
  have_header "sys/vfs.h"
34
23
  }
35
24
 
@@ -19,7 +19,14 @@
19
19
 
20
20
  static struct statfs *get_statfs( VALUE);
21
21
 
22
- static ID id_mul;
22
+ static ID id_mul = 0;
23
+
24
+ static const rb_data_type_t fsstat_data_type = {
25
+ "supplement:statfs",
26
+ { NULL, &ruby_xfree, NULL, NULL},
27
+ 0, 0, RUBY_TYPED_FREE_IMMEDIATELY
28
+ };
29
+
23
30
 
24
31
  /*
25
32
  * Document-class: Filesys
@@ -43,7 +50,8 @@ static ID id_mul;
43
50
  VALUE
44
51
  rb_fsstat_s_alloc( VALUE klass)
45
52
  {
46
- return Data_Wrap_Struct( klass, NULL, &free, (struct statfs *) NULL);
53
+ struct statfs *s;
54
+ return TypedData_Make_Struct( klass, struct statfs, &fsstat_data_type, s);
47
55
  }
48
56
 
49
57
  /*
@@ -57,56 +65,22 @@ rb_fsstat_s_alloc( VALUE klass)
57
65
  VALUE
58
66
  rb_fsstat_init( VALUE obj, VALUE dname)
59
67
  {
60
- struct statfs st, *nst;
68
+ struct statfs *st;
61
69
 
62
- SafeStringValue( dname);
70
+ TypedData_Get_Struct( obj, struct statfs, &fsstat_data_type, st);
63
71
 
64
- if (statfs( StringValueCStr( dname), &st) == -1)
72
+ SafeStringValue( dname);
73
+ if (statfs( StringValueCStr( dname), st) == -1)
65
74
  rb_sys_fail( RSTRING_PTR(dname));
66
- if (DATA_PTR(obj)) {
67
- free( DATA_PTR(obj));
68
- DATA_PTR(obj) = NULL;
69
- }
70
- nst = ALLOC(struct statfs);
71
- *nst = st;
72
- DATA_PTR(obj) = nst;
73
-
74
75
  return Qnil;
75
76
  }
76
77
 
77
- /* :nodoc: */
78
- VALUE
79
- rb_fsstat_init_copy( VALUE copy, VALUE orig)
80
- {
81
- struct statfs *nst;
82
-
83
- if (copy == orig)
84
- return orig;
85
-
86
- rb_check_frozen( copy);
87
- if (!rb_obj_is_instance_of( orig, rb_obj_class( copy)))
88
- rb_raise(rb_eTypeError, "wrong argument class");
89
- if (DATA_PTR(copy)) {
90
- free( DATA_PTR(copy));
91
- DATA_PTR(copy) = NULL;
92
- }
93
- if (DATA_PTR(orig)) {
94
- nst = ALLOC(struct statfs);
95
- *nst = *(struct statfs *) DATA_PTR(orig);
96
- DATA_PTR(copy) = nst;
97
- }
98
-
99
- return copy;
100
- }
101
78
 
102
- /* :nodoc: */
103
79
  struct statfs *
104
80
  get_statfs( VALUE self)
105
81
  {
106
82
  struct statfs *st;
107
- Data_Get_Struct(self, struct statfs, st);
108
- if (!st)
109
- rb_raise( rb_eTypeError, "uninitialized Filesys::Stat");
83
+ TypedData_Get_Struct( self, struct statfs, &fsstat_data_type, st);
110
84
  return st;
111
85
  }
112
86
 
@@ -360,12 +334,11 @@ void Init_filesys( void)
360
334
  VALUE rb_cFilesys;
361
335
  VALUE rb_cFilesysStat;
362
336
 
363
- rb_cFilesys = rb_define_class( "Filesys", rb_cObject);
337
+ rb_cFilesys = rb_define_module( "Filesys");
364
338
 
365
339
  rb_cFilesysStat = rb_define_class_under( rb_cFilesys, "Stat", rb_cObject);
366
- rb_define_alloc_func( rb_cFilesysStat, rb_fsstat_s_alloc);
340
+ rb_define_alloc_func( rb_cFilesysStat, rb_fsstat_s_alloc);
367
341
  rb_define_method( rb_cFilesysStat, "initialize", rb_fsstat_init, 1);
368
- rb_define_method( rb_cFilesysStat, "initialize_copy", rb_fsstat_init_copy, 1);
369
342
 
370
343
  rb_define_method( rb_cFilesysStat, "type", rb_fsstat_type , 0);
371
344
  rb_define_method( rb_cFilesysStat, "bsize", rb_fsstat_bsize , 0);
@@ -31,20 +31,14 @@ rb_locked_init( int argc, VALUE *argv, VALUE self)
31
31
  #ifdef FEATURE_OLD_IO_FUNCTIONS
32
32
  rb_io_t *fptr;
33
33
  #endif
34
- #ifdef HAVE_FUNC_RB_THREAD_WAIT_FOR
35
34
  struct timeval time;
36
- #endif
37
35
  int op;
38
36
 
39
37
  #ifdef FEATURE_OLD_IO_FUNCTIONS
40
38
  GetOpenFile( self, fptr);
41
39
  #endif
42
40
 
43
- #ifdef FEATURE_SUPER_KWARGS
44
41
  rb_call_super_kw(argc, argv, RB_PASS_CALLED_KEYWORDS);
45
- #else
46
- rb_call_super( argc, argv);
47
- #endif
48
42
 
49
43
  #ifdef FEATURE_OLD_IO_FUNCTIONS
50
44
  op = fptr->mode & FMODE_WRITABLE ? LOCK_EX : LOCK_SH;
@@ -72,13 +66,9 @@ rb_locked_init( int argc, VALUE *argv, VALUE self)
72
66
  if (rb_respond_to( self, id_lock_failed))
73
67
  rb_funcall( self, id_lock_failed, 0);
74
68
  else {
75
- #ifdef HAVE_FUNC_RB_THREAD_WAIT_FOR
76
69
  time.tv_sec = 0;
77
70
  time.tv_usec = 100 * 1000;
78
71
  rb_thread_wait_for(time);
79
- #else
80
- rb_thread_polling();
81
- #endif
82
72
  }
83
73
  break;
84
74
  default:
@@ -5,8 +5,8 @@
5
5
  #include <ruby/io.h>
6
6
 
7
7
 
8
- static ID id_accept_orig;
9
- static ID id_close;
8
+ static ID id_accept_orig = 0;
9
+ static ID id_close = 0;
10
10
 
11
11
  static VALUE socket_close( VALUE);
12
12
 
data/lib/supplement.c CHANGED
@@ -10,34 +10,20 @@
10
10
  #include <ruby/io.h>
11
11
  #include <ruby/re.h>
12
12
 
13
- #ifdef FEATURE_THREAD_EXCLUSIVE
14
- #ifdef HAVE_HEADER_RUBYSIG_H
15
- #include <rubysig.h>
16
- #endif
17
- #endif
18
-
19
13
 
20
14
  static void supplement_ary_assure_notempty( VALUE);
21
15
  static VALUE supplement_index_blk( VALUE);
22
16
  static VALUE supplement_index_ref( VALUE, VALUE);
23
17
  static VALUE supplement_rindex_blk( VALUE);
24
18
  static VALUE supplement_rindex_ref( VALUE, VALUE);
25
- #ifdef FEATURE_ARRAY_INDEX_WITH_BLOCK
26
- static VALUE supplement_index_val( VALUE, VALUE);
27
- static VALUE supplement_rindex_val( VALUE, VALUE);
28
- #endif
29
19
  static VALUE supplement_do_unumask( VALUE);
30
- #ifdef FEATURE_THREAD_EXCLUSIVE
31
- static VALUE bsruby_set_thread_critical( VALUE);
32
- #endif
33
-
34
20
 
35
21
 
36
- static ID id_delete_at;
37
- static ID id_cmp;
38
- static ID id_eqq;
39
- static ID id_mkdir;
40
- static ID id_index;
22
+ static ID id_delete_at = 0;
23
+ static ID id_cmp = 0;
24
+ static ID id_eqq = 0;
25
+ static ID id_mkdir = 0;
26
+ static ID id_index = 0;
41
27
 
42
28
 
43
29
 
@@ -102,31 +88,6 @@ rb_obj_nil_if( VALUE obj, VALUE val)
102
88
  * Document-module: Kernel
103
89
  */
104
90
 
105
- #ifdef FEATURE_KERNEL_TAP
106
-
107
- /*
108
- * call-seq:
109
- * tap { |x| ... } -> obj
110
- *
111
- * Yields <code>x</code> to the block, and then returns <code>x</code>.
112
- * The primary purpose of this method is to "tap into" a method chain,
113
- * in order to perform operations on intermediate results within the chain.
114
- *
115
- * (1..10) .tap { |x| puts "original: #{x.inspect}" }
116
- * .to_a .tap { |x| puts "array: #{x.inspect}" }
117
- * .select { |x| x%2==0 } .tap { |x| puts "evens: #{x.inspect}" }
118
- * .map { |x| x*x } .tap { |x| puts "squares: #{x.inspect}" }
119
- *
120
- */
121
-
122
- VALUE
123
- rb_krn_tap( VALUE obj)
124
- {
125
- rb_yield( obj);
126
- return obj;
127
- }
128
-
129
- #endif
130
91
 
131
92
  /*
132
93
  * call-seq:
@@ -362,30 +323,6 @@ rb_str_cut_bang( VALUE str, VALUE len)
362
323
  }
363
324
 
364
325
 
365
- #ifdef FEATURE_STRING_CLEAR
366
-
367
- /*
368
- * call-seq:
369
- * clear -> self
370
- *
371
- * Set to empty string. Equivalent to <code>str.replace ""</code>.
372
- *
373
- * a = "hello" #=> "hello"
374
- * a.clear #=> ""
375
- * a.empty? #=> true
376
- */
377
-
378
- VALUE
379
- rb_str_clear( VALUE str)
380
- {
381
- rb_str_modify( str);
382
- rb_str_resize( str, 0);
383
- return str;
384
- }
385
-
386
- #endif
387
-
388
-
389
326
  /*
390
327
  * call-seq:
391
328
  * head( n = 1) -> str
@@ -454,81 +391,97 @@ rb_str_tail( int argc, VALUE *argv, VALUE str)
454
391
  }
455
392
 
456
393
 
457
- #ifdef FEATURE_STRING_START_WITH
458
-
459
394
  /*
460
395
  * call-seq:
461
- * start_with?( oth) -> true or false
396
+ * axe( n = 80) -> str
462
397
  *
463
- * Checks whether the head is <code>oth</code>.
398
+ * Cut off everthing beyond then <code>n</code>th character. Replace the
399
+ * last bytes by ellipses.
464
400
  *
465
- * "sys-apps".start_with?( "sys-") #=> true
401
+ * a = "Redistribution and use in source and binary forms, with or without"
402
+ * a.axe( 16) #=> "Redistributio..."
466
403
  */
467
404
 
468
405
  VALUE
469
- rb_str_start_with_p( VALUE str, VALUE oth)
406
+ rb_str_axe( int argc, VALUE *argv, VALUE str)
470
407
  {
471
- return NIL_P( rb_str_starts_with_p( str, oth)) ? Qfalse : Qtrue;
472
- }
408
+ VALUE n;
409
+ VALUE ret;
410
+ long newlen, oldlen;
473
411
 
412
+ if (rb_scan_args( argc, argv, "01", &n) == 1 && !NIL_P( n))
413
+ newlen = NUM2LONG( n);
414
+ else
415
+ newlen = 80;
416
+ if (newlen < 0)
417
+ return Qnil;
474
418
 
475
- /*
476
- * call-seq:
477
- * end_with?( oth) -> true or false
478
- *
479
- * Checks whether the tail is <code>oth</code>.
480
- *
481
- * "sys-apps".end_with?( "-apps") #=> true
482
- */
419
+ oldlen = rb_str_strlen( str);
420
+ if (newlen < oldlen) {
421
+ VALUE ell;
422
+ long e;
483
423
 
484
- VALUE
485
- rb_str_end_with_p( VALUE str, VALUE oth)
486
- {
487
- return NIL_P( rb_str_ends_with_p( str, oth)) ? Qfalse : Qtrue;
424
+ ell = rb_str_new2( "...");
425
+ e = rb_str_strlen( ell);
426
+ if (newlen > e) {
427
+ ret = rb_str_substr( str, 0, newlen - e);
428
+ rb_str_append( ret, ell);
429
+ } else
430
+ ret = rb_str_substr( str, 0, newlen);
431
+ } else
432
+ ret = str;
433
+ return ret;
488
434
  }
489
435
 
490
- #endif
491
436
 
492
437
  /*
493
438
  * call-seq:
494
- * starts_with?( oth) -> nil or int
439
+ * starts_with?( *oth) -> nil or int
495
440
  *
496
- * Checks whether the head is <code>oth</code>. Returns length of
497
- * <code>oth</code> when matching.
441
+ * Checks whether the head is one of <code>oth</code>. Returns the position
442
+ * where the match ends.
498
443
  *
499
444
  * "sys-apps".starts_with?( "sys-") #=> 4
500
445
  *
501
446
  * Caution! The Ruby 1.9.3 method #start_with? (notice the missing s)
502
- * just returns +true+ or +false+.
447
+ * just returns +true+ or +false+. Mnemonics: "s" = prepare for
448
+ * <code>#slice</code>.
503
449
  */
504
450
 
505
451
  VALUE
506
- rb_str_starts_with_p( VALUE str, VALUE oth)
452
+ rb_str_starts_with_p( int argc, VALUE *argv, VALUE str)
507
453
  {
508
- long i;
509
- char *s, *o;
510
- VALUE ost;
454
+ int j;
511
455
 
512
- ost = rb_string_value( &oth);
513
- i = RSTRING_LEN( ost);
514
- if (i > RSTRING_LEN( str))
515
- return Qnil;
516
- s = RSTRING_PTR( str);
517
- o = RSTRING_PTR( ost);
518
- for (; i; i--, s++, o++) {
519
- if (*s != *o)
456
+ for (j = 0; j < argc; j++) {
457
+ long i;
458
+ char *s, *o;
459
+ VALUE ost;
460
+ VALUE oth = argv[ j];
461
+
462
+ ost = rb_string_value( &oth);
463
+ i = RSTRING_LEN( ost);
464
+ if (i > RSTRING_LEN( str))
520
465
  return Qnil;
466
+ s = RSTRING_PTR( str);
467
+ o = RSTRING_PTR( ost);
468
+ for (; i; i--, s++, o++) {
469
+ if (*s != *o)
470
+ break;
471
+ }
472
+ if (!i)
473
+ return INT2FIX( rb_str_strlen( ost));
521
474
  }
522
- return INT2FIX( rb_str_strlen( ost));
475
+ return Qnil;
523
476
  }
524
477
 
525
478
 
526
479
  /*
527
480
  * call-seq:
528
- * ends_with?( oth) -> nil or int
481
+ * ends_with?( *oth) -> nil or int
529
482
  *
530
- * Checks whether the tail is <code>oth</code>. Returns the position
531
- * where <code>oth</code> starts when matching.
483
+ * Checks whether the tail is one of <code>oth</code>. Returns the position
484
+ * where the match starts.
532
485
  *
533
486
  * "sys-apps".ends_with?( "-apps") #=> 3
534
487
  *
@@ -537,84 +490,70 @@ rb_str_starts_with_p( VALUE str, VALUE oth)
537
490
  */
538
491
 
539
492
  VALUE
540
- rb_str_ends_with_p( VALUE str, VALUE oth)
493
+ rb_str_ends_with_p( int argc, VALUE *argv, VALUE str)
541
494
  {
542
- long i;
543
- char *s, *o;
544
- VALUE ost;
495
+ int j;
545
496
 
546
- ost = rb_string_value( &oth);
547
- i = RSTRING_LEN( ost);
548
- if (i > RSTRING_LEN( str))
549
- return Qnil;
550
- s = RSTRING_END( str);
551
- o = RSTRING_END( ost);
552
- for (; i; i--)
553
- if (*--s != *--o)
497
+ for (j = 0; j < argc; j++) {
498
+ long i;
499
+ char *s, *o;
500
+ VALUE ost;
501
+ VALUE oth = argv[ j];
502
+
503
+ ost = rb_string_value( &oth);
504
+ i = RSTRING_LEN( ost);
505
+ if (i > RSTRING_LEN( str))
554
506
  return Qnil;
555
- return INT2FIX( rb_str_strlen( str) - rb_str_strlen( ost));
507
+ s = RSTRING_END( str);
508
+ o = RSTRING_END( ost);
509
+ for (; i; i--)
510
+ if (*--s != *--o)
511
+ break;
512
+ if (!i)
513
+ return INT2FIX( rb_str_strlen( str) - rb_str_strlen( ost));
514
+ }
515
+ return Qnil;
556
516
  }
557
517
 
558
- #ifdef FEATURE_STRING_ORD
559
518
 
560
519
  /*
561
520
  * call-seq:
562
- * ord() -> nil or int
521
+ * starts_with?( oth) -> nil or int
522
+ *
523
+ * Checks whether the head is <code>oth</code>. Returns length of
524
+ * <code>oth</code> when matching.
563
525
  *
564
- * Returns the ASCII value of the first character, if any.
526
+ * :"sys-apps".starts_with?( "sys-") #=> 4
565
527
  *
566
- * Caution! For UTF-8 characters, this will return the first byte's value.
567
- * This will do no harm in Ruby 1.8 but the standard Ruby 1.9 +String#ord+
568
- * returns the first codepoint. Please do not overwrite that method.
528
+ * Caution! The Ruby 1.9.3 method #start_with? (notice the missing s)
529
+ * just returns +true+ or +false+. Mnemonics: "s" = prepare for
530
+ * <code>#slice</code>.
569
531
  */
570
532
 
571
- VALUE rb_str_ord( VALUE str)
533
+ VALUE
534
+ rb_sym_starts_with_p( int argc, VALUE *argv, VALUE sym)
572
535
  {
573
- return RSTRING_LEN( str) > 0 ? INT2FIX( RSTRING_PTR( str)[ 0]) : Qnil;
536
+ return rb_str_starts_with_p(argc, argv, rb_sym2str(sym));
574
537
  }
575
538
 
576
- #endif
577
539
 
578
540
  /*
579
541
  * call-seq:
580
- * axe( n = 80) -> str
542
+ * ends_with?( oth) -> nil or int
581
543
  *
582
- * Cut off everthing beyond then <code>n</code>th character. Replace the
583
- * last bytes by ellipses.
544
+ * Checks whether the tail is <code>oth</code>. Returns the position
545
+ * where <code>oth</code> starts when matching.
584
546
  *
585
- * a = "Redistribution and use in source and binary forms, with or without"
586
- * a.axe( 16) #=> "Redistributio..."
547
+ * :"sys-apps".ends_with?( "-apps") #=> 3
548
+ *
549
+ * Caution! The Ruby 1.9.3 method #start_with? (notice the missing s)
550
+ * just returns +true+ or +false+.
587
551
  */
588
552
 
589
553
  VALUE
590
- rb_str_axe( int argc, VALUE *argv, VALUE str)
554
+ rb_sym_ends_with_p( int argc, VALUE *argv, VALUE sym)
591
555
  {
592
- VALUE n;
593
- VALUE ret;
594
- long newlen, oldlen;
595
-
596
- if (rb_scan_args( argc, argv, "01", &n) == 1 && !NIL_P( n))
597
- newlen = NUM2LONG( n);
598
- else
599
- newlen = 80;
600
- if (newlen < 0)
601
- return Qnil;
602
-
603
- oldlen = rb_str_strlen( str);
604
- if (newlen < oldlen) {
605
- VALUE ell;
606
- long e;
607
-
608
- ell = rb_str_new2( "...");
609
- e = rb_str_strlen( ell);
610
- if (newlen > e) {
611
- ret = rb_str_substr( str, 0, newlen - e);
612
- rb_str_append( ret, ell);
613
- } else
614
- ret = rb_str_substr( str, 0, newlen);
615
- } else
616
- ret = str;
617
- return ret;
556
+ return rb_str_ends_with_p(argc, argv, rb_sym2str(sym));
618
557
  }
619
558
 
620
559
 
@@ -683,42 +622,24 @@ rb_num_sqrt( VALUE num)
683
622
  return rb_float_new( sqrt( RFLOAT_VALUE( rb_Float( num))));
684
623
  }
685
624
 
625
+ /*
626
+ * Document-class: Rational
627
+ */
628
+
686
629
  /*
687
630
  * call-seq:
688
- * num.cbrt -> num
631
+ * rat.inv -> rat
689
632
  *
690
- * Cube root.
633
+ * The reciprocal.
691
634
  *
692
- * 27.cbrt #=> 3.0
635
+ * 5/7r.inv #=> 7/5r
693
636
  */
694
637
 
695
638
  VALUE
696
- rb_num_cbrt( VALUE num)
639
+ rb_rat_inverse( VALUE rat)
697
640
  {
698
- #if HAVE_FUNC_CBRT
699
- return rb_float_new( cbrt( RFLOAT_VALUE( rb_Float( num))));
700
- #else
701
- double n;
702
- int neg;
703
- int i;
704
-
705
- n = RFLOAT_VALUE( rb_Float( num));
706
- if ((neg = n < 0))
707
- n = -n;
708
- n = sqrt( sqrt( n));
709
- i = 2;
710
- for (;;) {
711
- double w = n;
712
- int j;
713
-
714
- for (j=i;j;--j) w = sqrt( w);
715
- i *= 2;
716
- w *= n;
717
- if (n == w) break;
718
- n = w;
719
- }
720
- return rb_float_new( neg ? -n : n);
721
- #endif
641
+ /* There is an internal function `rb_ration_reciprocal()`, but that cannot be reached from here. */
642
+ return rb_Rational( rb_rational_den( rat), rb_rational_num( rat));
722
643
  }
723
644
 
724
645
 
@@ -962,96 +883,6 @@ supplement_rindex_blk( VALUE ary)
962
883
  }
963
884
 
964
885
 
965
- #ifdef FEATURE_ARRAY_INDEX_WITH_BLOCK
966
-
967
- /*
968
- * call-seq:
969
- * index( obj) -> int or nil
970
- * index() { |elem| ... } -> int or nil
971
- *
972
- * Returns the index of the first object in <code>self</code> such that
973
- * is <code>==</code> to <code>obj</code> or the <em>block</em> returns
974
- * <code>true</code>. If no match is found, <code>nil</code> is
975
- * returned.
976
- *
977
- * a = %w(a b c d e)
978
- * a.index("b") #=> 1
979
- * a.index("z") #=> nil
980
- * a.index { |e| e >= "b" } #=> 1
981
- * a.index { |e| e >= "q" } #=> nil
982
- */
983
-
984
- VALUE
985
- rb_ary_index( int argc, VALUE *argv, VALUE ary)
986
- {
987
- VALUE val;
988
-
989
- if (rb_scan_args( argc, argv, "01", &val) == 1) {
990
- if (rb_block_given_p())
991
- rb_warning( "given block not used");
992
- return supplement_index_val( ary, val);
993
- } else
994
- return supplement_index_blk( ary);
995
- return Qnil;
996
- }
997
-
998
- VALUE
999
- supplement_index_val( VALUE ary, VALUE val)
1000
- {
1001
- long i;
1002
-
1003
- for (i = 0; i < RARRAY_LEN( ary); i++)
1004
- if (rb_equal( RARRAY_PTR( ary)[ i], val))
1005
- return LONG2NUM( i);
1006
- return Qnil;
1007
- }
1008
-
1009
-
1010
- /*
1011
- * call-seq:
1012
- * rindex( obj) -> int or nil
1013
- * rindex() { |elem| ... } -> int or nil
1014
- *
1015
- * Returns the index of the first object in <code>self</code> such that
1016
- * is <code>==</code> to <code>obj</code> or the <em>block</em> returns
1017
- * <code>true</code>. If no match is found, <code>nil</code> is
1018
- * returned. Search from right to left.
1019
- *
1020
- * a = %w(a b c d e)
1021
- * a.rindex("b") #=> 1
1022
- * a.rindex("z") #=> nil
1023
- * a.rindex { |e| e >= "b" } #=> 4
1024
- * a.rindex { |e| e >= "q" } #=> nil
1025
- */
1026
-
1027
- VALUE
1028
- rb_ary_rindex( int argc, VALUE *argv, VALUE ary)
1029
- {
1030
- VALUE val;
1031
-
1032
- if (rb_scan_args( argc, argv, "01", &val) == 1) {
1033
- if (rb_block_given_p())
1034
- rb_warning( "given block not used");
1035
- return supplement_rindex_val( ary, val);
1036
- } else
1037
- return supplement_rindex_blk( ary);
1038
- return Qnil;
1039
- }
1040
-
1041
- VALUE
1042
- supplement_rindex_val( VALUE ary, VALUE val)
1043
- {
1044
- long i;
1045
-
1046
- for (i = RARRAY_LEN( ary); i;)
1047
- if (rb_equal( RARRAY_PTR( ary)[ --i], val))
1048
- return LONG2NUM( i);
1049
- return Qnil;
1050
- }
1051
-
1052
- #endif
1053
-
1054
-
1055
886
  /*
1056
887
  * Document-class: Hash
1057
888
  */
@@ -1186,31 +1017,6 @@ rb_dir_s_mkdir_bang( int argc, VALUE *argv, VALUE dir)
1186
1017
  }
1187
1018
 
1188
1019
 
1189
- #ifdef FEATURE_DIR_CHILDREN
1190
-
1191
- /*
1192
- * call-seq:
1193
- * children() -> ary
1194
- *
1195
- * Entries without <code>"."</code> and <code>".."</code>.
1196
- *
1197
- */
1198
-
1199
- VALUE
1200
- rb_dir_children( VALUE self)
1201
- {
1202
- VALUE e;
1203
-
1204
- e = rb_funcall( self, rb_intern( "entries"), 0);
1205
- rb_ary_delete( e, rb_str_new( ".", 1));
1206
- rb_ary_delete( e, rb_str_new( "..", 2));
1207
- return e;
1208
- }
1209
-
1210
- #endif
1211
-
1212
-
1213
-
1214
1020
  /*
1215
1021
  * Document-class: Match
1216
1022
  */
@@ -1310,40 +1116,6 @@ rb_struct_fields( int argc, VALUE *argv, VALUE strct)
1310
1116
  }
1311
1117
 
1312
1118
 
1313
- #ifdef FEATURE_THREAD_EXCLUSIVE
1314
-
1315
- /*
1316
- * Document-class: Thread
1317
- */
1318
-
1319
- /*
1320
- * call-seq:
1321
- * Thread.exclusive { ... } -> obj
1322
- *
1323
- * Sets the global ``thread critical'' condition temporarily. Return
1324
- * value is the object returned by the <em>block</em>.
1325
- */
1326
-
1327
- VALUE
1328
- rb_thread_exclusive( void)
1329
- {
1330
- VALUE old_tc = rb_thread_critical;
1331
-
1332
- rb_thread_critical = Qtrue;
1333
- return rb_ensure( rb_yield, Qnil, bsruby_set_thread_critical, old_tc);
1334
- }
1335
-
1336
- VALUE
1337
- bsruby_set_thread_critical( VALUE c)
1338
- {
1339
- rb_thread_critical = c;
1340
- return Qnil;
1341
- }
1342
-
1343
- #endif
1344
-
1345
-
1346
-
1347
1119
  /*
1348
1120
  * Document-class: Struct
1349
1121
  */
@@ -1363,7 +1135,6 @@ bsruby_set_thread_critical( VALUE c)
1363
1135
  */
1364
1136
 
1365
1137
 
1366
-
1367
1138
  /*
1368
1139
  * Document-class: Object
1369
1140
  */
@@ -1393,9 +1164,6 @@ void Init_supplement( void)
1393
1164
  {
1394
1165
  rb_define_method( rb_cObject, "new_string", rb_obj_new_string, 0);
1395
1166
  rb_define_method( rb_cObject, "nil_if", rb_obj_nil_if, 1);
1396
- #ifdef FEATURE_KERNEL_TAP
1397
- rb_define_method( rb_mKernel, "tap", rb_krn_tap, 0);
1398
- #endif
1399
1167
  rb_define_method( rb_mKernel, "tap!", rb_krn_tap_bang, 0);
1400
1168
  rb_define_method( rb_mKernel, "with", rb_krn_with, 0);
1401
1169
 
@@ -1409,28 +1177,19 @@ void Init_supplement( void)
1409
1177
  rb_define_method( rb_cString, "notempty?", rb_str_notempty_p, 0);
1410
1178
  rb_define_method( rb_cString, "eat", rb_str_eat, -1);
1411
1179
  rb_define_method( rb_cString, "cut!", rb_str_cut_bang, 1);
1412
- #ifdef FEATURE_STRING_CLEAR
1413
- rb_define_method( rb_cString, "clear", rb_str_clear, 0);
1414
- #endif
1415
1180
  rb_define_method( rb_cString, "head", rb_str_head, -1);
1416
1181
  rb_define_method( rb_cString, "rest", rb_str_rest, -1);
1417
1182
  rb_define_method( rb_cString, "tail", rb_str_tail, -1);
1418
- #ifdef FEATURE_STRING_START_WITH
1419
- rb_define_method( rb_cString, "start_with?", rb_str_start_with_p, 1);
1420
- rb_define_method( rb_cString, "end_with?", rb_str_end_with_p, 1);
1421
- #endif
1422
- rb_define_method( rb_cString, "starts_with?", rb_str_starts_with_p, 1);
1423
- rb_define_method( rb_cString, "ends_with?", rb_str_ends_with_p, 1);
1424
- rb_define_alias( rb_cString, "starts_with", "start_with?");
1425
- rb_define_alias( rb_cString, "ends_with", "end_with?");
1426
- #ifdef FEATURE_STRING_ORD
1427
- rb_define_method( rb_cString, "ord", rb_str_ord, 0);
1428
- #endif
1429
1183
  rb_define_method( rb_cString, "axe", rb_str_axe, -1);
1184
+ rb_define_method( rb_cString, "starts_with?", rb_str_starts_with_p, -1);
1185
+ rb_define_method( rb_cString, "ends_with?", rb_str_ends_with_p, -1);
1186
+ rb_define_method( rb_cSymbol, "starts_with?", rb_sym_starts_with_p, -1);
1187
+ rb_define_method( rb_cSymbol, "ends_with?", rb_sym_ends_with_p, -1);
1430
1188
 
1431
1189
  rb_define_method( rb_cNumeric, "grammatical", rb_num_grammatical, 2);
1432
1190
  rb_define_method( rb_cNumeric, "sqrt", rb_num_sqrt, 0);
1433
- rb_define_method( rb_cNumeric, "cbrt", rb_num_cbrt, 0);
1191
+
1192
+ rb_define_method( rb_cRational, "inv", rb_rat_inverse, 0);
1434
1193
 
1435
1194
  rb_define_method( rb_cArray, "notempty?", rb_ary_notempty_p, 0);
1436
1195
  rb_define_method( rb_cArray, "first=", rb_ary_first_set, 1);
@@ -1440,10 +1199,6 @@ void Init_supplement( void)
1440
1199
  rb_define_method( rb_cArray, "range", rb_ary_range, 0);
1441
1200
  rb_define_method( rb_cArray, "pick", rb_ary_pick, -1);
1442
1201
  rb_define_method( rb_cArray, "rpick", rb_ary_rpick, -1);
1443
- #ifdef FEATURE_ARRAY_INDEX_WITH_BLOCK
1444
- rb_define_method( rb_cArray, "index", rb_ary_index, -1);
1445
- rb_define_method( rb_cArray, "rindex", rb_ary_rindex, -1);
1446
- #endif
1447
1202
 
1448
1203
  rb_define_method( rb_cHash, "notempty?", rb_hash_notempty_p, 0);
1449
1204
 
@@ -1451,19 +1206,11 @@ void Init_supplement( void)
1451
1206
 
1452
1207
  rb_define_singleton_method( rb_cDir, "current", rb_dir_s_current, 0);
1453
1208
  rb_define_singleton_method( rb_cDir, "mkdir!", rb_dir_s_mkdir_bang, -1);
1454
- #ifdef FEATURE_DIR_CHILDREN
1455
- rb_define_method( rb_cDir, "children", rb_dir_children, 0);
1456
- #endif
1457
1209
  rb_define_alias( rb_cDir, "entries!", "children");
1458
1210
 
1459
1211
  rb_define_method( rb_cMatch, "begin", rb_match_begin, -1);
1460
1212
  rb_define_method( rb_cMatch, "end", rb_match_end, -1);
1461
1213
 
1462
- #ifdef FEATURE_THREAD_EXCLUSIVE
1463
- rb_define_singleton_method( rb_cThread, "exclusive",
1464
- rb_thread_exclusive, 0);
1465
- #endif
1466
-
1467
1214
  rb_define_alias( rb_singleton_class( rb_cStruct), "[]", "new");
1468
1215
  rb_define_method( rb_cStruct, "fields", rb_struct_fields, -1);
1469
1216
  rb_define_alias( rb_cStruct, "fetch_values", "fields");
data/lib/supplement.h CHANGED
@@ -11,9 +11,6 @@
11
11
 
12
12
  extern VALUE rb_obj_new_string( VALUE);
13
13
  extern VALUE rb_obj_nil_if( VALUE, VALUE);
14
- #ifdef FEATURE_KERNEL_TAP
15
- extern VALUE rb_krn_tap( VALUE);
16
- #endif
17
14
  extern VALUE rb_krn_tap_bang( VALUE);
18
15
  extern VALUE rb_krn_with( VALUE);
19
16
 
@@ -26,26 +23,18 @@ extern VALUE rb_str_new_string( VALUE);
26
23
  extern VALUE rb_str_notempty_p( VALUE);
27
24
  extern VALUE rb_str_eat( int, VALUE *, VALUE);
28
25
  extern VALUE rb_str_cut_bang( VALUE, VALUE);
29
- #ifdef FEATURE_STRING_CLEAR
30
- extern VALUE rb_str_clear( VALUE);
31
- #endif
32
26
  extern VALUE rb_str_head( int, VALUE *, VALUE);
33
27
  extern VALUE rb_str_rest( int, VALUE *, VALUE);
34
28
  extern VALUE rb_str_tail( int, VALUE *, VALUE);
35
- #ifdef FEATURE_STRING_START_WITH
36
- extern VALUE rb_str_start_with_p( VALUE, VALUE);
37
- extern VALUE rb_str_end_with_p( VALUE, VALUE);
38
- #endif
39
- extern VALUE rb_str_starts_with_p( VALUE, VALUE);
40
- extern VALUE rb_str_ends_with_p( VALUE, VALUE);
41
- #ifdef FEATURE_STRING_ORD
42
- extern VALUE rb_str_ord( VALUE);
43
- #endif
44
29
  extern VALUE rb_str_axe( int, VALUE *, VALUE);
30
+ extern VALUE rb_str_starts_with_p( int argc, VALUE *argv, VALUE);
31
+ extern VALUE rb_str_ends_with_p( int argc, VALUE *argv, VALUE);
32
+ extern VALUE rb_sym_starts_with_p( int argc, VALUE *argv, VALUE);
33
+ extern VALUE rb_sym_ends_with_p( int argc, VALUE *argv, VALUE);
45
34
 
46
35
  extern VALUE rb_num_grammatical( VALUE, VALUE, VALUE);
47
36
  extern VALUE rb_num_sqrt( VALUE);
48
- extern VALUE rb_num_cbrt( VALUE);
37
+ extern VALUE rb_rat_inverse( VALUE);
49
38
 
50
39
  extern VALUE rb_ary_notempty_p( VALUE);
51
40
  extern VALUE rb_ary_first_set( VALUE, VALUE);
@@ -54,25 +43,16 @@ extern VALUE rb_ary_indexes( VALUE);
54
43
  extern VALUE rb_ary_range( VALUE);
55
44
  extern VALUE rb_ary_pick( int, VALUE *, VALUE);
56
45
  extern VALUE rb_ary_rpick( int, VALUE *, VALUE);
57
- #ifdef FEATURE_ARRAY_INDEX_WITH_BLOCK
58
- extern VALUE rb_ary_index( int, VALUE *, VALUE);
59
- extern VALUE rb_ary_rindex( int, VALUE *, VALUE);
60
- #endif
61
46
 
62
47
  extern VALUE rb_hash_notempty_p( VALUE);
63
48
 
64
49
  extern VALUE rb_file_s_umask( int, VALUE *, VALUE);
65
50
  extern VALUE rb_dir_s_current( VALUE);
66
51
  extern VALUE rb_dir_s_mkdir_bang( int, VALUE *, VALUE);
67
- extern VALUE rb_dir_children( VALUE);
68
52
 
69
53
  extern VALUE rb_match_begin( int, VALUE *, VALUE);
70
54
  extern VALUE rb_match_end( int, VALUE *, VALUE);
71
55
 
72
- #ifdef FEATURE_THREAD_EXCLUSIVE
73
- extern VALUE rb_thread_exclusive( void);
74
- #endif
75
-
76
56
  extern VALUE rb_struct_fields( int, VALUE *, VALUE);
77
57
 
78
58
  extern VALUE rb_nil_to_bool( VALUE);
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: supplement
3
3
  version: !ruby/object:Gem::Version
4
- version: '2.26'
4
+ version: '2.29'
5
5
  platform: ruby
6
6
  authors:
7
7
  - Bertram Scharpf
@@ -46,10 +46,10 @@ extensions:
46
46
  - lib/mkrf_conf
47
47
  extra_rdoc_files:
48
48
  - LICENSE
49
- - README
49
+ - README.md
50
50
  files:
51
51
  - LICENSE
52
- - README
52
+ - README.md
53
53
  - examples/teatimer
54
54
  - lib/Rakefile
55
55
  - lib/mkrf_conf
@@ -74,16 +74,14 @@ homepage: https://github.com/BertramScharpf/ruby-supplement
74
74
  licenses:
75
75
  - BSD-2-Clause
76
76
  metadata: {}
77
- rdoc_options:
78
- - "--main"
79
- - README
77
+ rdoc_options: []
80
78
  require_paths:
81
79
  - lib
82
80
  required_ruby_version: !ruby/object:Gem::Requirement
83
81
  requirements:
84
82
  - - ">="
85
83
  - !ruby/object:Gem::Version
86
- version: 2.0.0
84
+ version: 3.1.0
87
85
  required_rubygems_version: !ruby/object:Gem::Requirement
88
86
  requirements:
89
87
  - - ">="
@@ -91,7 +89,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
91
89
  version: '0'
92
90
  requirements:
93
91
  - Ruby and the autorake gem
94
- rubygems_version: 3.6.7
92
+ rubygems_version: 3.7.1
95
93
  specification_version: 4
96
94
  summary: Simple Ruby extensions
97
95
  test_files: []
data/README DELETED
@@ -1,68 +0,0 @@
1
- = supplement 2.26 -- Useful Ruby enhancements
2
-
3
-
4
- Some simple Ruby extensions.
5
-
6
-
7
- == Author
8
-
9
- Bertram Scharpf <software@bertram-scharpf.de>
10
-
11
-
12
- == Motivation
13
-
14
- The original motivation was my conviction that a language that has a
15
- Numeric#nonzero? method induces a programming style that as well demands
16
- for a String#notempty? method.
17
-
18
-
19
-
20
- == Description
21
-
22
- These are methods on standard classes that didn't manage to become part of
23
- the Ruby interpreter. (Although, some did in the meantime.)
24
-
25
- They are all very small, most of them have less than 15 lines of code.
26
- So they would not be a weight in the Ruby interpreter but it is very
27
- difficult to convince a majority that they belong there.
28
-
29
- The methods won't be useful for everybody but some programmers may like
30
- to make them part of their programming style.
31
-
32
- If you like to get taunted, then go to the Ruby mailing list and propose
33
- one of them to be included into the Ruby standard.
34
-
35
-
36
-
37
- == Intention
38
-
39
- In my own code I use quite often a method <code>String#notempty?</code>
40
- that does almost the same as <code>Numeric#nonzero?</code>. Every
41
- attempt proposing it for the Ruby standard implementation has failed;
42
- the discussion evolves the same every time.
43
-
44
- Now here it is where I can just point to.
45
-
46
-
47
-
48
- == Contents (uncomplete)
49
-
50
- * String#notempty?
51
- * String#clear
52
- * String#head
53
- * String#tail
54
- * String#rest
55
- * String#start_with?
56
- * String#end_with?
57
- * Array#notempty?
58
- * Array#first=/last=
59
- * Hash#notempty?
60
- * Struct.[]
61
- * Integer.roman
62
- * Date.easter
63
- * TCPServer/UNIXServer.accept with a code block
64
- * File system stats
65
- * Process.renice
66
- * Interval timer
67
- * LockedFile
68
-