Руби, это позволяет конструкторам декартовых произведений? - PullRequest
0 голосов
/ 27 октября 2010

Как гласит заголовок, допускает ли Ruby декартовы типы продуктов? Я нигде ничего не могу найти.

Спасибо

1 Ответ

3 голосов
/ 28 октября 2010

Ruby вообще не допускает типы , по крайней мере, в том смысле, что вы, кажется, используете слово «тип». Следовательно, он также явно не поддерживает типы продуктов.

Ruby - это так называемый язык с "динамической типизацией" (использующий прагматическое определение языка "программист-жаргон") или нетипизированный язык (использующий математическое, теоретико-типовое определение), так что говорим о "продукте" типы "просто не имеет смысла вообще.

Или, если хотите, вы можете увидеть динамически типизированный язык как статически типизированный язык только с одним типом, который является типом суммы всех динамических типов.

Однако, вы можете , очевидно, построить значения , что будет иметь тип продукта, если у Ruby есть типы на всех :

class Tuple
  include Enumerable; include Comparable

  class << self
    alias_method :[], :new

    def call(length)
      class_name = :"Tuple#{length}"
      return const_get class_name if const_defined? class_name
      const_set class_name, Class.new(self) {
        (@length = length).times do |i| define_method :"_#{i+1}" do @ary[i] end end
      }
    end
  end

  def to_s; "(#{@ary.join(', ')})" end
  def inspect; "#<#{self.class} (#{@ary.map(&:inspect).join(', ')})>" end
  def to_a; @ary.dup end
  def [](*args) @ary[*args] end
  def each(*args, &block) @ary.each(*args, &block) end

  def <=>(other)
    raise TypeError unless other.is_a? self.class
    raise TypeError unless each_with_index.all? {|el, i| other.instance_variable_get(:@ary)[i].instance_of?(el.class) }
    map.with_index {|el, i| el <=> other.instance_variable_get(:@ary)[i] }.find(0) {|cmp| !cmp.zero? }
  end

  def initialize(*args)
    raise ArgumentError unless args.length == self.class.instance_variable_get(:@length)
    (@ary = args).freeze
  end
end

Это даст вам возможность создавать n-кортежи, которые, конечно, являются особыми случаями типов продуктов. Например, это:

t3 = Tuple.(3)[1, :two, 'three']

создаст тройку с типом кортежа (Fixnum, Symbol, String), который является частным случаем типа продукта Fixnum × Symbol × String. Но нет способа представить и / или обеспечить эти типы в Ruby.

Если вы хотите глубже изучить системы типов для Ruby, проект Diamondback Ruby является хорошей отправной точкой. Например, типов кортежей , которые являются экземплярами типов продуктов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...