计算与另一条记录关联的记录数量

时间:2015-02-23 16:33:25

标签: ruby-on-rails ruby ruby-on-rails-3 methods count

在我的Ruby on Rails应用程序中,我正在创建一个影院系统,在预订/新页面上,我允许用户通过下拉菜单选择所需的座位数量。但我想要做的是显示屏幕上当前空闲的座位数,例如,如果一个屏幕有50个座位而且已经预订了7个我希望系统显示:"有43个座位可用。 "我知道我需要一个方法,但我不确定如何实现它以及如何显示此消息。

值得注意的是,一个座位只能预订一个,因此对其他人来说是免费的,这意味着该方法必须能够计算可用于该节目的座位数量。

有人可以帮忙。

预订/ form.html.erb:

<%= form_for @booking do |f| %>
    <%= f.hidden_field :user_id %>
    <%= f.hidden_field :showing_id %>

    <%= image_tag "thor_hammer.jpg",:size => "900x250" %>
    <h1>NEW BOOKING:</h1>
    <tr>
        <td width="350px">
            <br><%= f.label :seats_quantity, 'Please Select The Amount of Seats Required:' %>
        </td>
        <td width="300px">
            <br><%= f.select :seats_quantity, '1'..'10' %><br>
        </td>
        <td width="300px">
            <div class="actions">
                 <br><%= f.submit 'Book Showing' %>
            </div>
            <br><%= render "/error_messages", :message_header => "Cannot save: ", :target => @booking %> 
        </td>
    </tr>
<% end %>

Screen.rb:

class Screen < ActiveRecord::Base
   has_many :seats
   has_many :showings
   def screens_info
       "#{name}"
   end
end

Seat.rb:

class Seat < ActiveRecord::Base
    belongs_to :screen
end

Booking.rb:

class Booking < ActiveRecord::Base
    belongs_to :user
    belongs_to :showing
end

Showing.rb:

class Showing < ActiveRecord::Base
   belongs_to :film
   has_many :bookings
   belongs_to :screen
end

架构:

create_table "bookings", force: :cascade do |t|
    t.integer  "user_id"
    t.integer  "showing_id"
    t.integer  "seats_quantity"
end

create_table "screens", force: :cascade do |t|
   t.string   "name"
end

create_table "showings", force: :cascade do |t|
   t.date     "show_date"
   t.time     "show_time"
   t.integer  "film_id"
   t.integer  "screen_id"
end

create_table "seats", force: :cascade do |t|
   t.string   "row_letter"
   t.integer  "row_number"
   t.integer  "screen_id"
end

值得注意的是,虽然seats表包含属性row_letterrow_number,但用户并未预订特定座位,只需要预订座位数量。

3 个答案:

答案 0 :(得分:1)

Screen课程中添加:

has_many :bookings, through: :showings

然后你的代码变成了:

def remaining_seats
  seats.count - bookings.sum(:seats_quantity)  # <-- edited when I realized there was a quantity in a booking
end

def screens_info
  "#{name} (#{remaining_seats}/#{seats.count} remaining)"
end

答案 1 :(得分:0)

您需要确定两个值:特定演出的总座位数以及已预订的座位数。假设您有两个名为scr_idshw_id的变量,其中第一个代表屏幕ID,第二个代表显示ID。

总席位数:

total_seats = Seat.where(screen_id: scr_id).count

总预订:

total_bookings = Booking.where(showing_id: shw_id).count

然后你只需要计算两者之间的差异。

available_seats = total_seats - total_bookings

编辑:具体实施

它应该作为屏幕模型中的方法实现:

def available_seatings(shw_id)
    total_seats = Seat.where(screen_id: this.id).count
    total_bookings = Booking.where(showing_id: shw_id).count
    return total_seats - total_bookings
end

然后在控制器中

@available_seatings = screen.available_seatings(shw_id)

然后,您可以在视图中使用@available_seatings变量

答案 2 :(得分:0)

修改

这样做的手动方式如下:

class Showing < ActiveRecord::Base
  def booked_seats
    bookings.pluck(:seats_quantity).sum
  end

  def available_seats
    seats.count - booked_seats
  end
end

<强> OLD

这看起来很好用于Rails'counter_cache

class Booking < ActiveRecord::Base
  belongs_to :showing, counter_cache: true
end

这会将计数存储在显示模型(您必须添加)的列中。然后,当您执行@showing.bookings.size(不计数)时,它将引用该列。

“通过此声明,Rails将使缓存值保持最新,然后返回该值以响应size方法。” http://guides.rubyonrails.org/association_basics.html