Project

General

Profile

Feature #15504

Updated by sawa (Tsuyoshi Sawada) over 3 years ago

# Abstract Abstrcat 

 Range is currently now non-frozen. How about freezing to freeze all of Range objects? 

 # Background 

 We froze freeze some types type of objects: objects, Numerics (r47523) and Symbols [Feature #8906]. 
 I believe that making objects immutable solves some kinds kind of programming difficulties. 

 `Range` is mutable mutable, at least when it is written as in Range literal. So we can write the following weird program: 

 ```ruby program.  

 ``` 
 2.times{ 
   r = (1..3) 
   p r.instance_variable_get(:@foo) 
   #=> 1st time: nil 
   #=> 2nd time: :bar 
   r.instance_variable_set(:@foo, :bar) 
 } 
 ``` 

 In in `range.c`, there is a comment (thanks znz-san): 

 ```c ``` 
 static void 
 range_modify(VALUE range) 
 { 
     rb_check_frozen(range); 
     /* Ranges are immutable, so that they should be initialized only once. */ 
     if (RANGE_EXCL(range) != Qnil) { 
	 rb_name_err_raise("`initialize' called twice", range, ID2SYM(idInitialize)); 
     } 
 } 
 ``` 

 # Patch 

 ``` 
 Index: range.c 
 =================================================================== 
 --- range.c 	 (リビジョン 66699) 
 +++ range.c 	 (作業コピー) 
 @@ -45,6 +45,8 @@ 
      RANGE_SET_EXCL(range, exclude_end); 
      RANGE_SET_BEG(range, beg); 
      RANGE_SET_END(range, end); 
 + 
 +      rb_obj_freeze(range); 
  } 
 
  VALUE 
 ``` 

 # Discussion 

 There are several usages usage of mutable Range in the tests. 

 * (1) Taint-flag taint-flag 
 * (2) Add add singleton methods. 
 * (3) Subclass subclass with mutable states 

 Maybe (2) and (3) are crucial. points. 

 Thanks, 
 Koichi

Back