Class: Struct
Class Method Summary collapse
-
.new ⇒ Object
Creates a new class, named by aString, containing accessor methods for the given symbols.
Instance Method Summary collapse
-
#==(other_struct) ⇒ Boolean
Equality---Returns
true
if other_struct is equal to this one: they must be of the same class as generated byStruct::new
, and the values of all instance variables must be equal (according toObject#==
). -
#[] ⇒ Object
Attribute Reference---Returns the value of the instance variable named by symbol, or indexed (0..length-1) by fixnum.
-
#[]= ⇒ Object
Attribute Assignment---Assigns to the instance variable named by symbol or fixnum the value obj and returns it.
-
#each {|obj| ... } ⇒ Object
Calls block once for each instance variable, passing the value as a parameter.
-
#each_pair {|sym, obj| ... } ⇒ Object
Calls block once for each instance variable, passing the name (as a symbol) and the value as parameters.
-
#eql? ⇒ Object
code-seq: struct.eql?(other) => true or false.
-
#hash ⇒ Fixnum
Return a hash value based on this struct's contents.
- #initialize ⇒ Object constructor
-
#initialize_copy ⇒ Object
:nodoc:.
-
#inspect ⇒ Object
Describe the contents of this struct in a string.
-
#length ⇒ Object
Returns the number of instance variables.
-
#members ⇒ Array
Returns an array of strings representing the names of the instance variables.
-
#select {|i| ... } ⇒ Array
Invokes the block passing in successive elements from struct, returning an array containing those elements for which the block returns a true value (equivalent to
Enumerable#select
). -
#size ⇒ Object
Returns the number of instance variables.
-
#to_a ⇒ Object
Returns the values for this instance as an array.
-
#to_s ⇒ Object
Describe the contents of this struct in a string.
-
#values ⇒ Object
Returns the values for this instance as an array.
-
#values_at(selector, ...) ⇒ Array
Returns an array containing the elements in self corresponding to the given selector(s).
Methods included from Enumerable
#all?, #any?, #collect, #count, #cycle, #detect, #drop, #drop_while, #each_cons, #each_slice, #each_with_index, #entries, #enum_cons, #enum_slice, #enum_with_index, #find, #find_all, #find_index, #first, #grep, #group_by, #include?, #inject, #map, #max, #max_by, #member?, #min, #min_by, #minmax, #minmax_by, #none?, #one?, #partition, #reduce, #reject, #reverse_each, #sort, #sort_by, #take, #take_while, #zip
Constructor Details
#initialize ⇒ Object
|
# File 'struct.c'
/*
*/
static VALUE
rb_struct_initialize(self, values)
VALUE self, values;
{
VALUE klass = rb_obj_class(self);
VALUE size;
long n;
rb_struct_modify(self);
size = rb_struct_iv_get(klass, "__size__");
n = FIX2LONG(size);
if (n < RARRAY(values)->len) {
rb_raise(rb_eArgError, "struct size differs");
}
MEMCPY(RSTRUCT(self)->ptr, RARRAY(values)->ptr, VALUE, RARRAY(values)->len);
if (n > RARRAY(values)->len) {
rb_mem_clear(RSTRUCT(self)->ptr+RARRAY(values)->len,
n-RARRAY(values)->len);
}
return Qnil;
}
|
Class Method Details
.new([aString][, aSym]) ⇒ Object .new(arg, ...) ⇒ Object .[](arg, ...) ⇒ Object
Creates a new class, named by aString, containing accessor methods for the given symbols. If the name aString is omitted, an anonymous structure class will be created. Otherwise, the name of this struct will appear as a constant in class Struct
, so it must be unique for all Struct
s in the system and should start with a capital letter. Assigning a structure class to a constant effectively gives the class the name of the constant.
Struct::new
returns a new Class
object, which can then be used to create specific instances of the new structure. The number of actual parameters must be less than or equal to the number of attributes defined for this class; unset parameters default to nil{}. Passing too many parameters will raise an EArgumentError.
The remaining methods listed in this section (class and instance) are defined for this generated class.
# Create a structure with a name in Struct
Struct.new("Customer", :name, :address) #=> Struct::Customer
Struct::Customer.new("Dave", "123 Main") #=> #<Struct::Customer name="Dave", address="123 Main">
# Create a structure named by its constant
Customer = Struct.new(:name, :address) #=> Customer
Customer.new("Dave", "123 Main") #=> #<Customer name="Dave", address="123 Main">
|
# File 'struct.c'
/*
* call-seq:
* Struct.new( [aString] [, aSym]+> ) => StructClass
* StructClass.new(arg, ...) => obj
* StructClass[arg, ...] => obj
*
* Creates a new class, named by <i>aString</i>, containing accessor
* methods for the given symbols. If the name <i>aString</i> is
* omitted, an anonymous structure class will be created. Otherwise,
* the name of this struct will appear as a constant in class
* <code>Struct</code>, so it must be unique for all
* <code>Struct</code>s in the system and should start with a capital
* letter. Assigning a structure class to a constant effectively gives
* the class the name of the constant.
*
* <code>Struct::new</code> returns a new <code>Class</code> object,
* which can then be used to create specific instances of the new
* structure. The number of actual parameters must be
* less than or equal to the number of attributes defined for this
* class; unset parameters default to \nil{}. Passing too many
* parameters will raise an \E{ArgumentError}.
*
* The remaining methods listed in this section (class and instance)
* are defined for this generated class.
*
* # Create a structure with a name in Struct
* Struct.new("Customer", :name, :address) #=> Struct::Customer
* Struct::Customer.new("Dave", "123 Main") #=> #<Struct::Customer name="Dave", address="123 Main">
*
* # Create a structure named by its constant
* Customer = Struct.new(:name, :address) #=> Customer
* Customer.new("Dave", "123 Main") #=> #<Customer name="Dave", address="123 Main">
*/
static VALUE
rb_struct_s_def(argc, argv, klass)
int argc;
VALUE *argv;
VALUE klass;
{
VALUE name, rest;
long i;
VALUE st;
ID id;
rb_scan_args(argc, argv, "1*", &name, &rest);
if (!NIL_P(name) && SYMBOL_P(name)) {
rb_ary_unshift(rest, name);
name = Qnil;
}
for (i=0; i<RARRAY(rest)->len; i++) {
id = rb_to_id(RARRAY(rest)->ptr[i]);
RARRAY(rest)->ptr[i] = ID2SYM(id);
}
st = make_struct(name, rest, klass);
if (rb_block_given_p()) {
rb_mod_module_eval(0, 0, st);
}
return st;
}
|
Instance Method Details
#==(other_struct) ⇒ Boolean
Equality---Returns true
if other_struct is equal to this one: they must be of the same class as generated by Struct::new
, and the values of all instance variables must be equal (according to Object#==
).
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joejr = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
jane = Customer.new("Jane Doe", "456 Elm, Anytown NC", 12345)
joe == joejr #=> true
joe == jane #=> false
|
# File 'struct.c'
/*
* call-seq:
* struct == other_struct => true or false
*
* Equality---Returns <code>true</code> if <i>other_struct</i> is
* equal to this one: they must be of the same class as generated by
* <code>Struct::new</code>, and the values of all instance variables
* must be equal (according to <code>Object#==</code>).
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joejr = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* jane = Customer.new("Jane Doe", "456 Elm, Anytown NC", 12345)
* joe == joejr #=> true
* joe == jane #=> false
*/
static VALUE
rb_struct_equal(s, s2)
VALUE s, s2;
{
long i;
if (s == s2) return Qtrue;
if (TYPE(s2) != T_STRUCT) return Qfalse;
if (rb_obj_class(s) != rb_obj_class(s2)) return Qfalse;
if (RSTRUCT(s)->len != RSTRUCT(s2)->len) {
rb_bug("inconsistent struct"); /* should never happen */
}
for (i=0; i<RSTRUCT(s)->len; i++) {
if (!rb_equal(RSTRUCT(s)->ptr[i], RSTRUCT(s2)->ptr[i])) return Qfalse;
}
return Qtrue;
}
|
#[](symbol) ⇒ Object #[](fixnum) ⇒ Object
Attribute Reference---Returns the value of the instance variable named by symbol, or indexed (0..length-1) by fixnum. Will raise NameError
if the named variable does not exist, or IndexError
if the index is out of range.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe["name"] #=> "Joe Smith"
joe[:name] #=> "Joe Smith"
joe[0] #=> "Joe Smith"
|
# File 'struct.c'
/*
* call-seq:
* struct[symbol] => anObject
* struct[fixnum] => anObject
*
* Attribute Reference---Returns the value of the instance variable
* named by <i>symbol</i>, or indexed (0..length-1) by
* <i>fixnum</i>. Will raise <code>NameError</code> if the named
* variable does not exist, or <code>IndexError</code> if the index is
* out of range.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
*
* joe["name"] #=> "Joe Smith"
* joe[:name] #=> "Joe Smith"
* joe[0] #=> "Joe Smith"
*/
VALUE
rb_struct_aref(s, idx)
VALUE s, idx;
{
long i;
if (TYPE(idx) == T_STRING || TYPE(idx) == T_SYMBOL) {
return rb_struct_aref_id(s, rb_to_id(idx));
}
i = NUM2LONG(idx);
if (i < 0) i = RSTRUCT(s)->len + i;
if (i < 0)
rb_raise(rb_eIndexError, "offset %ld too small for struct(size:%ld)",
i, RSTRUCT(s)->len);
if (RSTRUCT(s)->len <= i)
rb_raise(rb_eIndexError, "offset %ld too large for struct(size:%ld)",
i, RSTRUCT(s)->len);
return RSTRUCT(s)->ptr[i];
}
|
#[]=(symbol) ⇒ Object #[]=(fixnum) ⇒ Object
Attribute Assignment---Assigns to the instance variable named by symbol or fixnum the value obj and returns it. Will raise a NameError
if the named variable does not exist, or an IndexError
if the index is out of range.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe["name"] = "Luke"
joe[:zip] = "90210"
joe.name #=> "Luke"
joe.zip #=> "90210"
|
# File 'struct.c'
/*
* call-seq:
* struct[symbol] = obj => obj
* struct[fixnum] = obj => obj
*
* Attribute Assignment---Assigns to the instance variable named by
* <i>symbol</i> or <i>fixnum</i> the value <i>obj</i> and
* returns it. Will raise a <code>NameError</code> if the named
* variable does not exist, or an <code>IndexError</code> if the index
* is out of range.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
*
* joe["name"] = "Luke"
* joe[:zip] = "90210"
*
* joe.name #=> "Luke"
* joe.zip #=> "90210"
*/
VALUE
rb_struct_aset(s, idx, val)
VALUE s, idx, val;
{
long i;
if (TYPE(idx) == T_STRING || TYPE(idx) == T_SYMBOL) {
return rb_struct_aset_id(s, rb_to_id(idx), val);
}
i = NUM2LONG(idx);
if (i < 0) i = RSTRUCT(s)->len + i;
if (i < 0) {
rb_raise(rb_eIndexError, "offset %ld too small for struct(size:%ld)",
i, RSTRUCT(s)->len);
}
if (RSTRUCT(s)->len <= i) {
rb_raise(rb_eIndexError, "offset %ld too large for struct(size:%ld)",
i, RSTRUCT(s)->len);
}
rb_struct_modify(s);
return RSTRUCT(s)->ptr[i] = val;
}
|
#each {|obj| ... } ⇒ Object
Calls block once for each instance variable, passing the value as a parameter.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.each {|x| puts(x) }
produces:
Joe Smith
123 Maple, Anytown NC
12345
|
# File 'struct.c'
/*
* call-seq:
* struct.each {|obj| block } => struct
*
* Calls <i>block</i> once for each instance variable, passing the
* value as a parameter.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.each {|x| puts(x) }
*
* <em>produces:</em>
*
* Joe Smith
* 123 Maple, Anytown NC
* 12345
*/
static VALUE
rb_struct_each(s)
VALUE s;
{
long i;
RETURN_ENUMERATOR(s, 0, 0);
for (i=0; i<RSTRUCT(s)->len; i++) {
rb_yield(RSTRUCT(s)->ptr[i]);
}
return s;
}
|
#each_pair {|sym, obj| ... } ⇒ Object
Calls block once for each instance variable, passing the name (as a symbol) and the value as parameters.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.each_pair {|name, value| puts("#{name} => #{value}") }
produces:
name => Joe Smith
address => 123 Maple, Anytown NC
zip => 12345
|
# File 'struct.c'
/*
* call-seq:
* struct.each_pair {|sym, obj| block } => struct
*
* Calls <i>block</i> once for each instance variable, passing the name
* (as a symbol) and the value as parameters.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.each_pair {|name, value| puts("#{name} => #{value}") }
*
* <em>produces:</em>
*
* name => Joe Smith
* address => 123 Maple, Anytown NC
* zip => 12345
*/
static VALUE
rb_struct_each_pair(s)
VALUE s;
{
VALUE members;
long i;
RETURN_ENUMERATOR(s, 0, 0);
members = rb_struct_members(s);
for (i=0; i<RSTRUCT(s)->len; i++) {
rb_yield_values(2, rb_ary_entry(members, i), RSTRUCT(s)->ptr[i]);
}
return s;
}
|
#eql? ⇒ Object
code-seq:
struct.eql?(other) => true or false
Two structures are equal if they are the same object, or if all their fields are equal (using eql?
).
|
# File 'struct.c'
/*
* code-seq:
* struct.eql?(other) => true or false
*
* Two structures are equal if they are the same object, or if all their
* fields are equal (using <code>eql?</code>).
*/
static VALUE
rb_struct_eql(s, s2)
VALUE s, s2;
{
long i;
if (s == s2) return Qtrue;
if (TYPE(s2) != T_STRUCT) return Qfalse;
if (rb_obj_class(s) != rb_obj_class(s2)) return Qfalse;
if (RSTRUCT(s)->len != RSTRUCT(s2)->len) {
rb_bug("inconsistent struct"); /* should never happen */
}
for (i=0; i<RSTRUCT(s)->len; i++) {
if (!rb_eql(RSTRUCT(s)->ptr[i], RSTRUCT(s2)->ptr[i])) return Qfalse;
}
return Qtrue;
}
|
#hash ⇒ Fixnum
Return a hash value based on this struct's contents.
|
# File 'struct.c'
/*
* call-seq:
* struct.hash => fixnum
*
* Return a hash value based on this struct's contents.
*/
static VALUE
rb_struct_hash(s)
VALUE s;
{
long i, h;
VALUE n;
h = rb_hash(rb_obj_class(s));
for (i = 0; i < RSTRUCT(s)->len; i++) {
h = (h << 1) | (h<0 ? 1 : 0);
n = rb_hash(RSTRUCT(s)->ptr[i]);
h ^= NUM2LONG(n);
}
return LONG2FIX(h);
}
|
#initialize_copy ⇒ Object
:nodoc:
|
# File 'struct.c'
/* :nodoc: */
static VALUE
rb_struct_init_copy(copy, s)
VALUE copy, s;
{
if (copy == s) return copy;
rb_check_frozen(copy);
if (!rb_obj_is_instance_of(s, rb_obj_class(copy))) {
rb_raise(rb_eTypeError, "wrong argument class");
}
if (RSTRUCT(copy)->len != RSTRUCT(s)->len) {
rb_raise(rb_eTypeError, "struct size mismatch");
}
MEMCPY(RSTRUCT(copy)->ptr, RSTRUCT(s)->ptr, VALUE, RSTRUCT(copy)->len);
return copy;
}
|
#to_s ⇒ String #inspect ⇒ String
Describe the contents of this struct in a string.
|
# File 'struct.c'
/*
* call-seq:
* struct.to_s => string
* struct.inspect => string
*
* Describe the contents of this struct in a string.
*/
static VALUE
rb_struct_inspect(s)
VALUE s;
{
if (rb_inspecting_p(s)) {
const char *cname = rb_class2name(rb_obj_class(s));
size_t len = strlen(cname) + 14;
VALUE str = rb_str_new(0, len);
snprintf(RSTRING(str)->ptr, len+1, "#<struct %s:...>", cname);
RSTRING(str)->len = strlen(RSTRING(str)->ptr);
return str;
}
return rb_protect_inspect(inspect_struct, s, 0);
}
|
#length ⇒ Fixnum #size ⇒ Fixnum
Returns the number of instance variables.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.length #=> 3
|
# File 'struct.c'
/*
* call-seq:
* struct.length => fixnum
* struct.size => fixnum
*
* Returns the number of instance variables.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.length #=> 3
*/
static VALUE
rb_struct_size(s)
VALUE s;
{
return LONG2FIX(RSTRUCT(s)->len);
}
|
#members ⇒ Array
Returns an array of strings representing the names of the instance variables.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.members #=> ["name", "address", "zip"]
|
# File 'struct.c'
/*
* call-seq:
* struct.members => array
*
* Returns an array of strings representing the names of the instance
* variables.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.members #=> ["name", "address", "zip"]
*/
static VALUE
rb_struct_members_m(obj)
VALUE obj;
{
return rb_struct_s_members_m(rb_obj_class(obj));
}
|
#select {|i| ... } ⇒ Array
Invokes the block passing in successive elements from struct, returning an array containing those elements for which the block returns a true value (equivalent to Enumerable#select
).
Lots = Struct.new(:a, :b, :c, :d, :e, :f)
l = Lots.new(11, 22, 33, 44, 55, 66)
l.select {|v| (v % 2).zero? } #=> [22, 44, 66]
|
# File 'struct.c'
/*
* call-seq:
* struct.select {|i| block } => array
*
* Invokes the block passing in successive elements from
* <i>struct</i>, returning an array containing those elements
* for which the block returns a true value (equivalent to
* <code>Enumerable#select</code>).
*
* Lots = Struct.new(:a, :b, :c, :d, :e, :f)
* l = Lots.new(11, 22, 33, 44, 55, 66)
* l.select {|v| (v % 2).zero? } #=> [22, 44, 66]
*/
static VALUE
rb_struct_select(argc, argv, s)
int argc;
VALUE *argv;
VALUE s;
{
VALUE result;
long i;
if (argc > 0) {
rb_raise(rb_eArgError, "wrong number of arguments (%d for 0)", argc);
}
result = rb_ary_new();
for (i = 0; i < RSTRUCT(s)->len; i++) {
if (RTEST(rb_yield(RSTRUCT(s)->ptr[i]))) {
rb_ary_push(result, RSTRUCT(s)->ptr[i]);
}
}
return result;
}
|
#length ⇒ Fixnum #size ⇒ Fixnum
Returns the number of instance variables.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.length #=> 3
|
# File 'struct.c'
/*
* call-seq:
* struct.length => fixnum
* struct.size => fixnum
*
* Returns the number of instance variables.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.length #=> 3
*/
static VALUE
rb_struct_size(s)
VALUE s;
{
return LONG2FIX(RSTRUCT(s)->len);
}
|
#to_a ⇒ Array #values ⇒ Array
Returns the values for this instance as an array.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.to_a[1] #=> "123 Maple, Anytown NC"
|
# File 'struct.c'
/*
* call-seq:
* struct.to_a => array
* struct.values => array
*
* Returns the values for this instance as an array.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.to_a[1] #=> "123 Maple, Anytown NC"
*/
static VALUE
rb_struct_to_a(s)
VALUE s;
{
return rb_ary_new4(RSTRUCT(s)->len, RSTRUCT(s)->ptr);
}
|
#to_s ⇒ String #inspect ⇒ String
Describe the contents of this struct in a string.
|
# File 'struct.c'
/*
* call-seq:
* struct.to_s => string
* struct.inspect => string
*
* Describe the contents of this struct in a string.
*/
static VALUE
rb_struct_inspect(s)
VALUE s;
{
if (rb_inspecting_p(s)) {
const char *cname = rb_class2name(rb_obj_class(s));
size_t len = strlen(cname) + 14;
VALUE str = rb_str_new(0, len);
snprintf(RSTRING(str)->ptr, len+1, "#<struct %s:...>", cname);
RSTRING(str)->len = strlen(RSTRING(str)->ptr);
return str;
}
return rb_protect_inspect(inspect_struct, s, 0);
}
|
#to_a ⇒ Array #values ⇒ Array
Returns the values for this instance as an array.
Customer = Struct.new(:name, :address, :zip)
joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
joe.to_a[1] #=> "123 Maple, Anytown NC"
|
# File 'struct.c'
/*
* call-seq:
* struct.to_a => array
* struct.values => array
*
* Returns the values for this instance as an array.
*
* Customer = Struct.new(:name, :address, :zip)
* joe = Customer.new("Joe Smith", "123 Maple, Anytown NC", 12345)
* joe.to_a[1] #=> "123 Maple, Anytown NC"
*/
static VALUE
rb_struct_to_a(s)
VALUE s;
{
return rb_ary_new4(RSTRUCT(s)->len, RSTRUCT(s)->ptr);
}
|
#values_at(selector, ...) ⇒ Array
Returns an array containing the elements in
_self_ corresponding to the given selector(s). The selectors
may be either integer indices or ranges.
See also </code>.select<code>.
a = %w{ a b c d e f }
a.values_at(1, 3, 5)
a.values_at(1, 3, 5, 7)
a.values_at(-1, -3, -5, -7)
a.values_at(1..3, 2...5)
|
# File 'struct.c'
/*
* call-seq:
* struct.values_at(selector,... ) => an_array
*
* Returns an array containing the elements in
* _self_ corresponding to the given selector(s). The selectors
* may be either integer indices or ranges.
* See also </code>.select<code>.
*
* a = %w{ a b c d e f }
* a.values_at(1, 3, 5)
* a.values_at(1, 3, 5, 7)
* a.values_at(-1, -3, -5, -7)
* a.values_at(1..3, 2...5)
*/
static VALUE
rb_struct_values_at(argc, argv, s)
int argc;
VALUE *argv;
VALUE s;
{
return rb_values_at(s, RSTRUCT(s)->len, argc, argv, struct_entry);
}
|