Natural Code

Code, science and politics.

stream_algorithm.rb

class Integer
  def chances_in(total)
    if (0...self) === rand(total)
      yield if block_given?
      return true
    else
      return false
    end
  end
end

class Array
  def random; self[rand(self.size)]; end
end

def fputs string
  puts string
  STDOUT.flush
end

def fprint string
  print string
  STDOUT.flush
end

class Stream
  attr_reader :length, :reader

  def initialize reader, opts={}
    @reader = reader
    @length = opts[:length] || 10
    @skew = opts[:skew] || nil
  end

  def start
    fputs "\n#{self.class.to_s} running!"

    1.upto(length) { next_item }; stop
    self
  end

  def stop
    fputs "Stream stopped."
    reader.display_results
  end

  def next_item
    reader.send( @skew && @skew[:percent].chances_in(100) ?
        @skew[:toward] : random_item! )
    sleep 0.1
  end
end

class NumberStream < Stream
  def random_item!
    rand( 10 )
  end
end

class LetterStream < Stream
  def random_item!
    ('a'..'z').to_a.random
  end
end

class StreamReader
  attr_reader :to_check

  def initialize
    fputs "Starting #{self.class.to_s}..."
  end

  def send element
    fprint "Reading : #{element}  "
    process element
  end

  def check *stats
    @to_check = stats

    stats.each do |stat|
      if stat == :most_frequent
        @most_frequent = nil
        @mf_count = 0
      else
        eval "@#{stat} = 0"
      end
    end

    self
  end

  def process element
    if to_check.include? :total_amount
      @total_amount += 1
    end

    if to_check.include? :biggest_element
      @biggest_element = element if element > @biggest_element
    end

    if to_check.include? :most_frequent
      if element == @most_frequent
        @mf_count += 1
      elsif @mf_count < 1
        @most_frequent = element
        @mf_count = 1
      else
        @mf_count -= 1
      end
      fputs "#{@most_frequent} x #{@mf_count}"
    end
  end

  def display_results
    to_check.each do |thing|
      display_name = thing.to_s.capitalize.gsub( /_/, ' ' )
      variable = eval "@#{thing}"

      fputs "#{display_name} : #{variable}"
    end
  end
end

1 Comment »

  1. [...] calls up this file. Next, I make a Stream Reader which I store in a [...]

    Pingback by Data streams, part 2 « Natural Code | July 15, 2008 | Reply


Leave a comment