Class: Ruport::DataSet
- Inherits:
-
Object
- Object
- Ruport::DataSet
- Includes:
- Enumerable
- Defined in:
- lib/ruport/data_set.rb
Overview
The DataSet is the core datastructure for Ruport. It provides methods that allow you to compare and combine query results, data loaded in from CSVs, and user-defined sets of data.
It is tightly integrated with Ruport’s formatting and query systems, so if you’d like to take advantage of these models, you will probably find DataSet useful.
Sample Usage:
my_data = [[1,2,3],[4,5,6],[7,8,9]]
ds = Ruport::DataSet.new([:col1, :col2, :col3],my_data)
ds << [ 10, 11, 12]
ds << { :col3 => 15, :col1 => 13, :col2 => 14 }
puts ds.select_columns(:col1, :col3).to_csv
Output:
col1,col3
1,3
4,6
7,9
10,12
13,15
The wild and crazy might want to try the Array hack:
puts [[1,2,3],[4,5,6],[7,8,9]].to_ds(%w[col1 col2 col3])
Output:
fields: ( col1, col2, col3 )
row0: ( 1, 2, 3 )
row1: ( 4, 5, 6 )
row2: ( 7, 8, 9 )
Instance Attribute Summary collapse
-
#data ⇒ Object
readonly
data holds the elements of the Row.
-
#default ⇒ Object
the default value to fill empty cells with.
-
#fields ⇒ Object
an array which contains column names.
Class Method Summary collapse
-
.load(source, default = "") ⇒ Object
Allows loading of CSV files or YAML dumps.
Instance Method Summary collapse
-
#<<(stuff, filler = @default) ⇒ Object
appends a row to the DataSet can be added as an array or a keyed hash-like object.
-
#==(data2) ⇒ Object
checks if one dataset equals another.
-
#[](index) ⇒ Object
Allows ordinal access to rows.
-
#[]=(index, value) ⇒ Object
allows setting of rows (providing a DataRow is passed in).
-
#as(format, &action) ⇒ Object
uses Format::Builder to render DataSets in various ready to output formats.
-
#clone ⇒ Object
provides a deep copy of the DataSet.
-
#each(&action) ⇒ Object
Iterates through the rows, yielding a DataRow for each.
-
#empty? ⇒ Boolean
Returns true if DataSet contains no rows, false otherwise.
-
#eql?(data2) ⇒ Boolean
checks if one dataset equals another.
-
#initialize(fields = [], content = nil, default = nil) ⇒ DataSet
constructor
DataSets must be given a set of fields to be defined.
-
#remove_columns(*fields) ⇒ Object
Returns a new DataSet with the specified fields removed.
-
#remove_columns!(*fields) ⇒ Object
removes the specified fields from this DataSet (DESTRUCTIVE!).
-
#select_columns(*fields) ⇒ Object
Returns a new DataSet composed of the fields specified.
-
#to_csv ⇒ Object
Converts a DataSet to CSV.
-
#to_html ⇒ Object
Converts a Dataset to html.
-
#to_s ⇒ Object
Readable string representation of the DataSet.
Constructor Details
#initialize(fields = [], content = nil, default = nil) ⇒ DataSet
DataSets must be given a set of fields to be defined.
These field names will define the columns for the DataSet and how you access them.
data = Ruport::DataSet.new %w[ id name phone ]
You can optionally pass in some content as well. (Must be Enumerable)
content = [ %w[ a1 gregory 203-525-0523 ],
%w[ a2 james 555-555-5555 ] ]
data = Ruport::DataSet.new(%w[ id name phone],content)
67 68 69 70 71 72 |
# File 'lib/ruport/data_set.rb', line 67 def initialize(fields=[], content=nil, default=nil) @fields = fields @data = [] @default = default content.each { |r| self << r } if content end |
Instance Attribute Details
#data ⇒ Object (readonly)
data holds the elements of the Row
81 82 83 |
# File 'lib/ruport/data_set.rb', line 81 def data @data end |
#default ⇒ Object
the default value to fill empty cells with
78 79 80 |
# File 'lib/ruport/data_set.rb', line 78 def default @default end |
#fields ⇒ Object
an array which contains column names
75 76 77 |
# File 'lib/ruport/data_set.rb', line 75 def fields @fields end |
Class Method Details
.load(source, default = "") ⇒ Object
142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 |
# File 'lib/ruport/data_set.rb', line 142 def self.load ( source, default="") case source when /\.(yaml|yml)/ return YAML.load(File.open(source)) when /\.csv/ csv_klass = defined?(FasterCSV) ? FasterCSV : CSV input = csv_klass.read(source) if source =~ /\.csv/ loaded_data = self.new loaded_data.fields = input[0] loaded_data.default = default input[1..-1].each { |row| loaded_data << row } return loaded_data else raise "Invalid file type" end end |
Instance Method Details
#<<(stuff, filler = @default) ⇒ Object
appends a row to the DataSet can be added as an array or a keyed hash-like object.
Columns left undefined will be filled with DataSet#default values.
data << [ 1, 2, 3 ]
data << { :some_field_name => 3, :other => 2, :another => 1 }
108 109 110 |
# File 'lib/ruport/data_set.rb', line 108 def << ( stuff, filler=@default ) @data << DataRow.new(stuff,@fields,:filler => filler) end |
#==(data2) ⇒ Object
checks if one dataset equals another
126 127 128 |
# File 'lib/ruport/data_set.rb', line 126 def ==(data2) eql?(data2) end |
#[](index) ⇒ Object
Allows ordinal access to rows
my_data[2] -> Ruport::DataRow
91 92 93 |
# File 'lib/ruport/data_set.rb', line 91 def [](index) @data[index] end |
#[]=(index, value) ⇒ Object
allows setting of rows (providing a DataRow is passed in)
96 97 98 99 |
# File 'lib/ruport/data_set.rb', line 96 def []=(index,value) throw "Invalid object type" unless value.kind_of?(DataRow) @data[index] = value end |
#as(format, &action) ⇒ Object
uses Format::Builder to render DataSets in various ready to output formats.
data.as(:html) -> String
data.as(:text) do |builder|
builder.range = 2..4 -> String
builder.header = "My Title"
end
To add new formats to this function, simply re-open Format::Builder and add methods like render_my_format_name
.
This will enable data.as(:my_format_name)
195 196 197 198 199 200 |
# File 'lib/ruport/data_set.rb', line 195 def as(format,&action) builder = Format::Builder.new( self ) builder.format = format action.call(builder) if block_given? builder.render end |
#clone ⇒ Object
provides a deep copy of the DataSet.
84 85 86 |
# File 'lib/ruport/data_set.rb', line 84 def clone DataSet.new(@fields,@data) end |
#each(&action) ⇒ Object
Iterates through the rows, yielding a DataRow for each.
160 161 162 |
# File 'lib/ruport/data_set.rb', line 160 def each(&action) @data.each(&action) end |
#empty? ⇒ Boolean
Returns true if DataSet contains no rows, false otherwise.
131 132 133 |
# File 'lib/ruport/data_set.rb', line 131 def empty? return @data.empty? end |
#eql?(data2) ⇒ Boolean
checks if one dataset equals another
113 114 115 116 117 118 119 120 121 122 123 |
# File 'lib/ruport/data_set.rb', line 113 def eql?(data2) return false unless ( @data.length == data2.data.length and @fields.eql?(data2.fields) ) @data.each_with_index do |row, r_index| row.each_with_index do |field, f_index| return false unless field.eql?(data2[r_index][f_index]) end end return true end |
#remove_columns(*fields) ⇒ Object
Returns a new DataSet with the specified fields removed
171 172 173 |
# File 'lib/ruport/data_set.rb', line 171 def remove_columns(*fields) select_fields(*(@fields-fields)) end |
#remove_columns!(*fields) ⇒ Object
removes the specified fields from this DataSet (DESTRUCTIVE!)
176 177 178 179 |
# File 'lib/ruport/data_set.rb', line 176 def remove_columns!(*fields) @fields -= fields @data = select_fields(*(@fields)).to_a end |
#select_columns(*fields) ⇒ Object
Returns a new DataSet composed of the fields specified.
165 166 167 168 |
# File 'lib/ruport/data_set.rb', line 165 def select_columns(*fields) rows = fields.inject([]) { |s,e| s << map { |row| row[e] } }.transpose my_data = DataSet.new(fields,rows) end |
#to_csv ⇒ Object
Converts a DataSet to CSV
203 |
# File 'lib/ruport/data_set.rb', line 203 def to_csv; as(:csv) end |
#to_html ⇒ Object
Converts a Dataset to html
206 |
# File 'lib/ruport/data_set.rb', line 206 def to_html; as(:html) end |
#to_s ⇒ Object
Readable string representation of the DataSet
209 |
# File 'lib/ruport/data_set.rb', line 209 def to_s; as(:text) end |