[英]Calculate Percent of total from scoped records and display virtual attributes (Rails / Active Record)
創建一個范圍,也許像這樣。
scope :mv, select('*,quantity*market_price as market_value, quantity*market_price/sum(quantity*market_price) as percent')
創建兩個虛擬屬性market_value和percent。 我遇到的問題是創建包含sum()的百分比。 如果添加sum(),則范圍返回一條記錄。
我需要計算market_value相對於范圍記錄集的總市場價值的百分比。
例:
1, market_value: 100, percent: .10
2, market_value: 100, percent: .10
3, market_value: 100, percent: .10
4, market_value: 100, percent: .10
5, market_value: 100, percent: .10
6, market_value: 500, percent: .50
Total is 1000
但是,如果我將其范圍設置為market_value <6,則應該看到
1, market_value: 100, percent: .20
2, market_value: 100, percent: .20
3, market_value: 100, percent: .20
4, market_value: 100, percent: .20
5, market_value: 100, percent: .20
Total 500
我該怎么做?
我創建了一個self.pct方法,但是self.pct方法的問題在於它需要在所有作用域之后運行。 如果重新界定范圍,則解決方案是錯誤的
至今,
class Position < ActiveRecord::Base
attr_accessible :account_id, :account_type, :market_price, :quantity, :report_date, :symbol
scope :long_only, where(:account_type => 'L')
scope :short_only, where(:account_type=>"S")
scope :equity_only, :conditions => ["symbol <> 'USD'"]
scope :mv, select('*,quantity*market_price as market_value, quantity*market_price/sum(quantity*market_price) as percent')
scope :mv1, lambda{|total| select(total) }
#the problem with the self.pct method is that it needs to be run after all the scopes. if rescoped, the solution is wrong
def self.pct
string="*,(quantity*market_price) as market_value, (market_price*quantity/#{sum_market_value}) as percent"
mv1(string)
end
def market_value
self.market_price*self.quantity
end
def self.sum_market_value
sum('quantity*market_price')
end
end
我不知道是否可以在單個查詢中執行此操作,但是我們可以在兩個查詢中獲取它:
require 'active_record'
ActiveRecord::Base.establish_connection adapter: 'sqlite3', database: ':memory:'
ActiveRecord::Schema.define do
self.verbose = false
create_table :positions do |t|
t.integer :quantity
t.integer :market_price
end
end
class Position < ActiveRecord::Base
def self.with_market_value
select "*,
quantity*market_price as market_value,
quantity*market_price/#{total.to_f} as percent"
end
def self.total
select('sum(quantity*market_price) as sum_of_market_values').first.sum_of_market_values
end
end
Position.create! quantity: 25, market_price: 4
Position.create! quantity: 25, market_price: 4
Position.create! quantity: 25, market_price: 4
Position.create! quantity: 25, market_price: 4
Position.create! quantity: 25, market_price: 4
Position.create! quantity: 25, market_price: 20
Position.with_market_value.map { |p| [p.market_value, p.percent] }
# => [[100, 0.1], [100, 0.1], [100, 0.1], [100, 0.1], [100, 0.1], [500, 0.5]]
Position.where('market_price < 10').with_market_value.map { |p| [p.market_value, p.percent] }
# => [[100, 0.2], [100, 0.2], [100, 0.2], [100, 0.2], [100, 0.2]]
# ** NOTE THAT IT EXECUTES EAGERLY **
Position.with_market_value.where('market_price < 10').map { |p| [p.market_value, p.percent] }
# => [[100, 0.1], [100, 0.1], [100, 0.1], [100, 0.1], [100, 0.1]]
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.