File: concrete-syntax/core/expression/binary/send.rb

Overview
Module Structure
Class Hierarchy
Code

Overview

Module Structure

  module: <Toplevel Module>
  module: Umu#6
  module: ConcreteSyntax#8
  module: Core#10
  module: Expression#12
has properties
function: make_message / 3 #290
function: make_apply_message / 3 #301
function: make_keyword_message / 3 #312
function: make_send / 4 #323
  module: Binary#14
  module: Send#16
  module: Message#18
  class: Abstract#20
  class: BasicMessage#24
inherits from
  Abstract ( Umu::ConcreteSyntax::Core::Expression::Binary::Send::Message )
has properties
attribute: sym [R] #25
attribute: exprs [R] #25
method: initialize / 3 #28
method: to_s #39
method: pretty_print / 1 #52
method: __desugar__ / 2 #69
  class: ApplyMessage#82
inherits from
  Abstract ( Umu::ConcreteSyntax::Core::Expression::Binary::Send::Message )
has properties
attribute: head_expr [R] #83
attribute: tail_exprs [R] #83
method: initialize / 3 #86
method: to_s #97
method: pretty_print / 1 #104
method: __desugar__ / 2 #117
  class: KeywordMessage#154
inherits from
  Abstract ( Umu::ConcreteSyntax::Core::Expression::Binary::Send::Message )
has properties
attribute: head_field [R] #155
attribute: tail_fields [R] #155
method: initialize / 3 #158
method: to_s #176
method: pretty_print / 1 #185
method: __desugar__ / 2 #201
  class: Entry#226
inherits from
  Abstract ( Umu::ConcreteSyntax::Core::Expression::Binary )
has properties
alias: lhs_expr lhs #227
alias: rhs_head_message rhs #228
attribute: rhs_tail_messages [R] #229
method: initialize / 4 #232
method: to_s #243
method: pretty_print / 1 #251
method: rhs_messages #260
method: __desugar__ / 2 #267

Code

   1  # coding: utf-8
   2  # frozen_string_literal: true
   3 
   4 
   5 
   6  module Umu
   7 
   8  module ConcreteSyntax
   9 
  10  module Core
  11 
  12  module Expression
  13 
  14  module Binary
  15 
  16  module Send
  17 
  18  module Message
  19 
  20  class Abstract < Expression::Abstract; end
  21 
  22 
  23 
  24  class BasicMessage < Abstract
  25      attr_reader :sym, :exprs
  26 
  27 
  28      def initialize(loc, sym, exprs)
  29          ASSERT.kind_of sym,     ::Symbol
  30          ASSERT.kind_of exprs,   ::Array
  31 
  32          super(loc)
  33 
  34          @sym    = sym
  35          @exprs  = exprs
  36      end
  37 
  38 
  39      def to_s
  40          format(".%s",
  41              if self.exprs.empty?
  42                  self.sym.to_s
  43              else
  44                  format "(%s %s)",
  45                          self.sym.to_s,
  46                          self.exprs.map(&:to_s).join(' ')
  47              end
  48          )
  49      end
  50 
  51 
  52      def pretty_print(q)
  53          PRT.group_for_enum(
  54              q,
  55 
  56              self.exprs,
  57 
  58              bb: format(self.exprs.empty? ? ".%s" : ".(%s ", self.sym.to_s),
  59 
  60              eb: self.exprs.empty? ? '' : ')',
  61 
  62              join: ' '
  63          )
  64      end
  65 
  66 
  67  private
  68 
  69      def __desugar__(env, event)
  70          new_env = env.enter event
  71 
  72          ASCE.make_message(
  73              self.loc,
  74              self.sym,
  75              self.exprs.map { |expr| expr.desugar(new_env) },
  76          )
  77      end
  78  end
  79 
  80 
  81 
  82  class ApplyMessage < Abstract
  83      attr_reader :head_expr, :tail_exprs
  84 
  85 
  86      def initialize(loc, head_expr, tail_exprs)
  87          ASSERT.kind_of head_expr,  CSCE::Abstract
  88          ASSERT.kind_of tail_exprs, ::Array
  89 
  90          super(loc)
  91 
  92          @head_expr   = head_expr
  93          @tail_exprs  = tail_exprs
  94      end
  95 
  96 
  97      def to_s
  98          format(".[%s]",
  99              ([self.head_expr.to_s] + self.tail_exprs).map(&:to_s).join(', ')
 100          )
 101      end
 102 
 103 
 104      def pretty_print(q)
 105          PRT.group_for_enum(
 106              q,
 107              [self.head_expr] + self.tail_exprs,
 108              bb: '.[',
 109              eb: ']',
 110              join: ', '
 111          )
 112      end
 113 
 114 
 115  private
 116 
 117      def __desugar__(env, event)
 118          new_env = env.enter event
 119 
 120          message = case self.tail_exprs.size
 121                  when 0
 122                      expr = [self.head_expr.desugar(new_env)]
 123 
 124                      ASCE.make_message self.loc, :apply, expr
 125                  when 1
 126                      exprs = [
 127                          self.head_expr.desugar(new_env),
 128                          self.tail_exprs[0].desugar(new_env)
 129                      ]
 130 
 131                      ASCE.make_message self.loc, :'apply-binary', exprs
 132                  else
 133                      second_expr, *tail_exprs = self.tail_exprs
 134                      exprs = [
 135                          self.head_expr.desugar(new_env),
 136 
 137                          second_expr.desugar(new_env),
 138 
 139                          ASCE.make_list(
 140                              tail_exprs[0].loc,
 141                              tail_exprs.map { |expr| expr.desugar new_env }
 142                          )
 143                      ]
 144 
 145                      ASCE.make_message self.loc, :'apply-nary', exprs
 146                  end
 147 
 148          ASSERT.kind_of message, ASCE::Binary::Send::Message
 149      end
 150  end
 151 
 152 
 153 
 154  class KeywordMessage < Abstract
 155      attr_reader :head_field, :tail_fields
 156 
 157 
 158      def initialize(loc, head_field, tail_fields)
 159          ASSERT.tuple_of    head_field,    [
 160                              CSCEU::Container::Named::Label, ::Object
 161                          ]
 162          ASSERT.opt_kind_of head_field[1], CSCE::Abstract
 163          ASSERT.kind_of     tail_fields,   ::Array
 164          tail_fields.each do |lab, expr|
 165              ASSERT.kind_of     lab,  CSCEU::Container::Named::Label
 166              ASSERT.opt_kind_of expr, CSCE::Abstract
 167          end
 168 
 169          super(loc)
 170 
 171          @head_field   = head_field
 172          @tail_fields  = tail_fields
 173      end
 174 
 175 
 176      def to_s
 177          format(".(%s)",
 178              ([self.head_field] + self.tail_fields).map { |lab, opt_expr|
 179                  lab.to_s + (opt_expr ? opt_expr.to_s : '')
 180              }.join(' ')
 181          )
 182      end
 183 
 184 
 185      def pretty_print(q)
 186          PRT.group_for_enum(
 187              q,
 188              [self.head_field] + self.tail_fields,
 189              bb: '.(',
 190              eb: ')',
 191              join: ' '
 192          ) do |lab, opt_expr|
 193              q.text lab.to_s
 194              q.text opt_expr.to_s if opt_expr
 195          end
 196      end
 197 
 198 
 199  private
 200 
 201      def __desugar__(env, event)
 202          new_env = env.enter event
 203 
 204          labels, exprs = (
 205              [self.head_field] + self.tail_fields
 206          ).inject([[], []]) { |(ls, es), fld|
 207              lab, opt_expr = fld
 208              expr = if opt_expr
 209                          opt_expr.desugar new_env
 210                      else
 211                          ASCE.make_identifier lab.loc, lab.sym
 212                      end
 213 
 214              [ls + [lab], es + [expr]]
 215          }
 216          sym = labels.map { |lab| lab.sym.to_s + ':' }.join.to_sym
 217 
 218          ASCE.make_message self.loc, sym, exprs
 219      end
 220  end
 221 
 222  end # Umu::ConcreteSyntax::Core::Expression::Binary::Send::Message
 223 
 224 
 225 
 226  class Entry < Binary::Abstract
 227      alias       lhs_expr            lhs
 228      alias       rhs_head_message    rhs
 229      attr_reader :rhs_tail_messages
 230 
 231 
 232      def initialize(loc, lhs_expr, rhs_head_message, rhs_tail_messages)
 233          ASSERT.kind_of lhs_expr,            CSCE::Abstract
 234          ASSERT.kind_of rhs_head_message,    Message::Abstract
 235          ASSERT.kind_of rhs_tail_messages,   ::Array
 236 
 237          super(loc, lhs_expr, rhs_head_message)
 238 
 239          @rhs_tail_messages = rhs_tail_messages
 240      end
 241 
 242 
 243      def to_s
 244          format("(%s)%s",
 245                  self.lhs_expr.to_s,
 246                  self.rhs_messages.map(&:to_s).join
 247          )
 248      end
 249 
 250 
 251      def pretty_print(q)
 252          PRT.group q, bb:'(', eb:')' do
 253              q.pp self.lhs_expr
 254          end
 255 
 256          PRT.group_for_enum q, self.rhs_messages
 257      end
 258 
 259 
 260      def rhs_messages
 261          [self.rhs_head_message] + self.rhs_tail_messages
 262      end
 263 
 264 
 265  private
 266 
 267      def __desugar__(env, event)
 268          new_env = env.enter event
 269 
 270          ASCE.make_send(
 271              self.loc,
 272              self.lhs_expr.desugar(new_env),
 273              self.rhs_head_message.desugar(new_env),
 274              self.rhs_tail_messages.map { |mess|
 275                  ASSERT.kind_of mess, Message::Abstract
 276 
 277                  mess.desugar(new_env)
 278              }
 279          )
 280      end
 281  end
 282 
 283  end # Umu::ConcreteSyntax::Core::Expression::Binary::Send
 284 
 285  end # Umu::ConcreteSyntax::Core::Expression::Binary
 286 
 287 
 288  module_function
 289 
 290      def make_message(loc, sym, exprs = [])
 291          ASSERT.kind_of loc,     LOC::Entry
 292          ASSERT.kind_of sym,     ::Symbol
 293          ASSERT.kind_of exprs,   ::Array
 294 
 295          Binary::Send::Message::BasicMessage.new(
 296              loc, sym, exprs.freeze
 297          ).freeze
 298      end
 299 
 300 
 301      def make_apply_message(loc, expr, exprs = [])
 302          ASSERT.kind_of loc,     LOC::Entry
 303          ASSERT.kind_of expr,    CSCE::Abstract
 304          ASSERT.kind_of exprs,   ::Array
 305 
 306          Binary::Send::Message::ApplyMessage.new(
 307              loc, expr, exprs.freeze
 308          ).freeze
 309      end
 310 
 311 
 312      def make_keyword_message(loc, field, fields = [])
 313          ASSERT.kind_of  loc,     LOC::Entry
 314          ASSERT.tuple_of field,   [CSCEU::Container::Named::Label, ::Object]
 315          ASSERT.kind_of  fields,  ::Array
 316 
 317          Binary::Send::Message::KeywordMessage.new(
 318              loc, field, fields.freeze
 319          ).freeze
 320      end
 321 
 322 
 323      def make_send(loc, lhs_expr, rhs_head_message, rhs_tail_messages = [])
 324          ASSERT.kind_of loc,                 LOC::Entry
 325          ASSERT.kind_of lhs_expr,            CSCE::Abstract
 326          ASSERT.kind_of rhs_head_message,    Binary::Send::Message::Abstract
 327          ASSERT.kind_of rhs_tail_messages,   ::Array
 328 
 329          Binary::Send::Entry.new(
 330              loc, lhs_expr, rhs_head_message, rhs_tail_messages.freeze
 331          ).freeze
 332      end
 333 
 334  end # Umu::ConcreteSyntax::Core::Expression
 335 
 336  end # Umu::ConcreteSyntax::Core
 337 
 338  end # Umu::ConcreteSyntax
 339 
 340  end # Umu