removed obsolete stat_histogram
This commit is contained in:
@@ -15,7 +15,6 @@ stack.lua
|
||||
post.lua
|
||||
sheet.lua
|
||||
history.lua
|
||||
stat_histogram.lua
|
||||
info.xml
|
||||
completion.xml
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
AuxVersion = '2.2.13'
|
||||
AuxVersion = '2.2.14'
|
||||
AuxAuthors = 'shirsig; Zerf; Zirco (Auctionator); Nimeral (Auctionator backport)'
|
||||
|
||||
local lastRightClickAction = GetTime()
|
||||
@@ -36,7 +36,7 @@ function Aux_OnLoad()
|
||||
local item_id, suffix_id = EnhTooltip.BreakLink(link)
|
||||
local item_key = (item_id or 0)..':'..(suffix_id or 0)
|
||||
|
||||
local auction_count, day_count, TDA, EMA5, EMA30 = Aux.history.get_price_data(item_key)
|
||||
local auction_count, day_count, TDA, EMA7, trend, variance = Aux.history.price_data(item_key)
|
||||
|
||||
if auction_count == 0 then
|
||||
EnhTooltip.AddLine('Never seen at auction', nil, true)
|
||||
@@ -45,21 +45,30 @@ function Aux_OnLoad()
|
||||
EnhTooltip.AddLine('Seen '..auction_count..' '..Aux_PluralizeIf('time', auction_count)..' at auction', nil, true)
|
||||
EnhTooltip.LineColor(0.5, 0.8, 0.1)
|
||||
|
||||
local market_value = Aux.history.get_market_value(item_key)
|
||||
local market_value = Aux.history.market_value(item_key)
|
||||
local trend_percentage = ceil((1 - trend) * 100)
|
||||
local market_value_line
|
||||
if count == 1 then
|
||||
EnhTooltip.AddLine('Market Value: '..Aux.util.money_string(market_value), nil, true)
|
||||
market_value_line = 'Market Value: '..Aux.util.money_string(market_value)
|
||||
else
|
||||
EnhTooltip.AddLine('Market Value: '..Aux.util.money_string(market_value * count)..' / '..Aux.util.money_string(market_value), nil, true)
|
||||
market_value_line = 'Market Value: '..Aux.util.money_string(market_value * count)..' / '..Aux.util.money_string(market_value)
|
||||
if trend_percentage > 0 then
|
||||
market_value_line = market_value_line..' ('..GREEN_FONT_COLOR_CODE..'+'..trend_percentage..'%'..GREEN_COLOR_CODE_CLOSE..')'
|
||||
elseif trend_percentage < 0 then
|
||||
market_value_line = market_value_line..' ('..RED_FONT_COLOR_CODE..trend_percentage..'%'..FONT_COLOR_CODE_CLOSE..')'
|
||||
end
|
||||
end
|
||||
EnhTooltip.AddLine(market_value_line, nil, true)
|
||||
EnhTooltip.LineColor(0.1,0.8,0.5)
|
||||
|
||||
-- EnhTooltip.AddLine('TDA: '..(TDA > 0 and Aux.util.money_string(TDA) or RED_FONT_COLOR_CODE..'n/a'..FONT_COLOR_CODE_CLOSE), nil, true)
|
||||
-- EnhTooltip.LineColor(0.1,0.8,0.5)
|
||||
-- EnhTooltip.AddLine('EMA5: '..(EMA5 > 0 and Aux.util.money_string(EMA5) or RED_FONT_COLOR_CODE..'n/a'..FONT_COLOR_CODE_CLOSE), nil, true)
|
||||
-- EnhTooltip.AddLine('EMA7: '..(EMA7 > 0 and Aux.util.money_string(EMA7) or RED_FONT_COLOR_CODE..'n/a'..FONT_COLOR_CODE_CLOSE), nil, true)
|
||||
-- EnhTooltip.LineColor(0.1,0.8,0.5)
|
||||
-- EnhTooltip.AddLine('EMA30: '..(EMA30 > 0 and Aux.util.money_string(EMA30) or RED_FONT_COLOR_CODE..'n/a'..FONT_COLOR_CODE_CLOSE), nil, true)
|
||||
-- EnhTooltip.AddLine('Trend: '..trend_percentage..'%', nil, true)
|
||||
-- EnhTooltip.LineColor(0.1,0.8,0.5)
|
||||
-- EnhTooltip.AddLine('SD: '..sqrt(variance), nil, true)
|
||||
-- EnhTooltip.LineColor(0.1,0.8,0.5)
|
||||
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
@@ -134,15 +134,15 @@ public.views = {
|
||||
title = 'Pct',
|
||||
width = 40,
|
||||
comparator = function(group1, group2)
|
||||
local market_price1 = Aux.history.get_market_value(group1[1].item_key)
|
||||
local market_price2 = Aux.history.get_market_value(group2[1].item_key)
|
||||
local market_price1 = Aux.history.market_value(group1[1].item_key)
|
||||
local market_price2 = Aux.history.market_value(group2[1].item_key)
|
||||
local factor1 = market_price1 > 0 and group1[1].buyout_price_per_unit / market_price1
|
||||
local factor2 = market_price2 > 0 and group2[1].buyout_price_per_unit / market_price2
|
||||
return Aux.util.compare(factor1, factor2, Aux.util.GT)
|
||||
end,
|
||||
cell_initializer = Aux.sheet.default_cell_initializer('RIGHT'),
|
||||
cell_setter = function(cell, group)
|
||||
local market_price = Aux.history.get_market_value(group[1].item_key)
|
||||
local market_price = Aux.history.market_value(group[1].item_key)
|
||||
|
||||
local pct = market_price > 0 and ceil(100 / market_price * group[1].buyout_price_per_unit)
|
||||
if not pct then
|
||||
@@ -487,15 +487,15 @@ public.views = {
|
||||
title = 'Pct',
|
||||
width = 40,
|
||||
comparator = function(row1, row2)
|
||||
local market_price1 = Aux.history.get_market_value(row1.item_key)
|
||||
local market_price2 = Aux.history.get_market_value(row2.item_key)
|
||||
local market_price1 = Aux.history.market_value(row1.item_key)
|
||||
local market_price2 = Aux.history.market_value(row2.item_key)
|
||||
local factor1 = market_price1 > 0 and row1.buyout_price_per_unit and row1.buyout_price_per_unit / market_price1
|
||||
local factor2 = market_price2 > 0 and row2.buyout_price_per_unit and row2.buyout_price_per_unit / market_price2
|
||||
return Aux.util.compare(factor1, factor2, Aux.util.GT)
|
||||
end,
|
||||
cell_initializer = Aux.sheet.default_cell_initializer('RIGHT'),
|
||||
cell_setter = function(cell, datum)
|
||||
local market_price = Aux.history.get_market_value(datum.item_key)
|
||||
local market_price = Aux.history.market_value(datum.item_key)
|
||||
|
||||
local pct = market_price > 0 and datum.buyout_price_per_unit and ceil(100 / market_price * datum.buyout_price_per_unit)
|
||||
if not pct then
|
||||
|
||||
+27
-21
@@ -2,7 +2,7 @@ local private, public = {}, {}
|
||||
Aux.history = public
|
||||
|
||||
private.PUSH_INTERVAL = 57600
|
||||
private.NEW_RECORD = '0#0#0#0#'
|
||||
private.NEW_RECORD = '0#0#0#1#0#'
|
||||
|
||||
function private.load_data()
|
||||
local dataset = Aux.persistence.load_dataset()
|
||||
@@ -10,15 +10,16 @@ function private.load_data()
|
||||
return dataset.history
|
||||
end
|
||||
|
||||
function public.read_record(item_key)
|
||||
function private.read_record(item_key)
|
||||
local data = private.load_data()
|
||||
local record = Aux.persistence.deserialize(data.item_data[item_key] or private.NEW_RECORD, '#')
|
||||
return {
|
||||
auction_count = tonumber(record[1]),
|
||||
day_count = tonumber(record[2]),
|
||||
EMA5 = tonumber(record[3]),
|
||||
EMA30 = tonumber(record[4]),
|
||||
histogram = Aux.util.map(Aux.persistence.deserialize(record[5], ';', 'x'), function(value)
|
||||
EMA7 = tonumber(record[3]),
|
||||
trend = tonumber(record[4]),
|
||||
variance = tonumber(record[5]),
|
||||
histogram = Aux.util.map(Aux.persistence.deserialize(record[6], ';', 'x'), function(value)
|
||||
return tonumber(value)
|
||||
end),
|
||||
}
|
||||
@@ -29,8 +30,9 @@ function private.write_record(item_key, record)
|
||||
data.item_data[item_key] = Aux.persistence.serialize({
|
||||
record.auction_count,
|
||||
record.day_count,
|
||||
record.EMA5,
|
||||
record.EMA30,
|
||||
record.EMA7,
|
||||
record.trend,
|
||||
record.variance,
|
||||
Aux.persistence.serialize(record.histogram, ';', 'x'),
|
||||
},'#')
|
||||
end
|
||||
@@ -49,7 +51,7 @@ function public.process_auction(auction_info)
|
||||
|
||||
local buyout = auction_info.buyout_price / auction_info.aux_quantity
|
||||
|
||||
local item_record = public.read_record(auction_info.item_key)
|
||||
local item_record = private.read_record(auction_info.item_key)
|
||||
|
||||
item_record.auction_count = item_record.auction_count + 1
|
||||
|
||||
@@ -64,18 +66,18 @@ function public.process_auction(auction_info)
|
||||
private.write_record(auction_info.item_key, item_record)
|
||||
end
|
||||
|
||||
function public.get_price_data(item_key)
|
||||
local item_record = public.read_record(item_key)
|
||||
return item_record.auction_count, item_record.day_count, private.daily_market_value(item_record.histogram), item_record.EMA5, item_record.EMA30
|
||||
function public.price_data(item_key)
|
||||
local item_record = private.read_record(item_key)
|
||||
return item_record.auction_count, item_record.day_count, private.daily_market_value(item_record.histogram), item_record.EMA7, item_record.trend, item_record.variance
|
||||
end
|
||||
|
||||
function public.get_market_value(item_key)
|
||||
local auction_count, day_count, daily_market_value, EMA5, EMA30 = public.get_price_data(item_key)
|
||||
function public.market_value(item_key)
|
||||
local auction_count, day_count, daily_market_value, EMA7, trend, variance = public.price_data(item_key)
|
||||
|
||||
if day_count == 0 then
|
||||
return daily_market_value
|
||||
else
|
||||
return EMA5
|
||||
return EMA7 * trend
|
||||
end
|
||||
end
|
||||
|
||||
@@ -110,18 +112,23 @@ function private.push_data()
|
||||
|
||||
for item_key, _ in pairs(item_data) do
|
||||
|
||||
local item_record = public.read_record(item_key)
|
||||
local item_record = private.read_record(item_key)
|
||||
|
||||
if getn(item_record.histogram) ~= 0 then
|
||||
|
||||
local daily_market_value = private.daily_market_value(item_record.histogram)
|
||||
|
||||
if item_record.day_count == 0 then
|
||||
item_record.EMA5 = daily_market_value
|
||||
item_record.EMA30 = daily_market_value
|
||||
item_record.EMA7 = daily_market_value
|
||||
item_record.trend = 1
|
||||
item_record.variance = 0
|
||||
else
|
||||
item_record.EMA5 = 2/3 * item_record.EMA5 + 1/3 * daily_market_value
|
||||
item_record.EMA30 = 13/14 * item_record.EMA30 + 1/14 * daily_market_value
|
||||
local new_trend = daily_market_value / item_record.EMA7
|
||||
local new_variance = (daily_market_value - item_record.EMA7) ^ 2
|
||||
|
||||
item_record.EMA7 = 3/4 * item_record.EMA7 + 1/4 * daily_market_value
|
||||
item_record.trend = 3/4 * item_record.trend + 1/4 * new_trend
|
||||
item_record.variance = 3/4 * item_record.variance + 1/4 * new_variance
|
||||
end
|
||||
|
||||
item_record.day_count = item_record.day_count + 1
|
||||
@@ -134,7 +141,7 @@ function private.push_data()
|
||||
data.next_push = time() + private.PUSH_INTERVAL
|
||||
end
|
||||
|
||||
--function private.max_heap(array)
|
||||
--function private.max_heap(array) -- might use a max heap to keep track of the n smallest values of the day instead of the histogram calculation
|
||||
-- local self = {}
|
||||
--
|
||||
-- local ROOT = 1
|
||||
@@ -160,7 +167,6 @@ end
|
||||
-- end
|
||||
--
|
||||
-- function self.extract(signature)
|
||||
-- return data[signature] ~= nil and data[signature] >= time()
|
||||
-- end
|
||||
--
|
||||
-- return self
|
||||
|
||||
@@ -147,15 +147,15 @@ public.views = {
|
||||
title = 'Pct',
|
||||
width = 40,
|
||||
comparator = function(group1, group2)
|
||||
local market_price1 = Aux.history.get_market_value(group1[1].item_key)
|
||||
local market_price2 = Aux.history.get_market_value(group2[1].item_key)
|
||||
local market_price1 = Aux.history.market_value(group1[1].item_key)
|
||||
local market_price2 = Aux.history.market_value(group2[1].item_key)
|
||||
local factor1 = market_price1 > 0 and group1[1].buyout_price_per_unit / market_price1
|
||||
local factor2 = market_price2 > 0 and group2[1].buyout_price_per_unit / market_price2
|
||||
return Aux.util.compare(factor1, factor2, Aux.util.GT)
|
||||
end,
|
||||
cell_initializer = Aux.sheet.default_cell_initializer('RIGHT'),
|
||||
cell_setter = function(cell, group)
|
||||
local market_price = Aux.history.get_market_value(group[1].item_key)
|
||||
local market_price = Aux.history.market_value(group[1].item_key)
|
||||
|
||||
local pct = market_price > 0 and ceil(100 / market_price * group[1].buyout_price_per_unit)
|
||||
if not pct then
|
||||
@@ -426,15 +426,15 @@ public.views = {
|
||||
title = 'Pct',
|
||||
width = 40,
|
||||
comparator = function(row1, row2)
|
||||
local market_price1 = Aux.history.get_market_value(row1.item_key)
|
||||
local market_price2 = Aux.history.get_market_value(row2.item_key)
|
||||
local market_price1 = Aux.history.market_value(row1.item_key)
|
||||
local market_price2 = Aux.history.market_value(row2.item_key)
|
||||
local factor1 = market_price1 > 0 and row1.buyout_price_per_unit and row1.buyout_price_per_unit / market_price1
|
||||
local factor2 = market_price2 > 0 and row2.buyout_price_per_unit and row2.buyout_price_per_unit / market_price2
|
||||
return Aux.util.compare(factor1, factor2, Aux.util.GT)
|
||||
end,
|
||||
cell_initializer = Aux.sheet.default_cell_initializer('RIGHT'),
|
||||
cell_setter = function(cell, datum)
|
||||
local market_price = Aux.history.get_market_value(datum.item_key)
|
||||
local market_price = Aux.history.market_value(datum.item_key)
|
||||
|
||||
local pct = market_price > 0 and datum.buyout_price_per_unit and ceil(100 / market_price * datum.buyout_price_per_unit)
|
||||
if not pct then
|
||||
|
||||
@@ -151,7 +151,6 @@ function scan_auctions_helper(i, n, k)
|
||||
if not snapshot.contains(auction_info.signature) then
|
||||
snapshot.add(auction_info.signature, auction_info.duration)
|
||||
Aux.history.process_auction(auction_info)
|
||||
-- Aux.stat_histogram.process_auction(auction_info)
|
||||
end
|
||||
else
|
||||
recurse()
|
||||
|
||||
@@ -6,11 +6,8 @@ function SlashCmdList.AUX(parameter)
|
||||
Aux.persistence.load_dataset().snapshot = {}
|
||||
Aux.log('Snapshot cleared.')
|
||||
elseif parameter == 'clear history' then
|
||||
Aux.persistence.load_dataset().stat_average_data = {}
|
||||
Aux.persistence.load_dataset().history = {}
|
||||
Aux.log('History cleared.')
|
||||
elseif parameter == 'clear histogram' then
|
||||
Aux.persistence.load_dataset().stat_histogram_data = {}
|
||||
Aux.log('Histogram data cleared.')
|
||||
elseif parameter == 'clear' then
|
||||
aux_database = {}
|
||||
Aux.log('Database cleared.')
|
||||
|
||||
@@ -1,180 +0,0 @@
|
||||
local private, public = {}, {}
|
||||
Aux.stat_histogram = public
|
||||
|
||||
private.NEW_RECORD = '0:0:0:0:'
|
||||
|
||||
function private.load_data()
|
||||
local dataset = Aux.persistence.load_dataset()
|
||||
dataset.stat_histogram_data = dataset.stat_histogram_data or { item_data = {} }
|
||||
return dataset.stat_histogram_data
|
||||
end
|
||||
|
||||
function private.read_current_record(item_key)
|
||||
if private.current_item_key ~= item_key then
|
||||
local data = private.load_data()
|
||||
local record = Aux.persistence.deserialize(data.item_data[item_key] or private.NEW_RECORD, ':')
|
||||
private.current_record = {
|
||||
min = tonumber(record[1]),
|
||||
max = tonumber(record[2]),
|
||||
step = tonumber(record[3]),
|
||||
count = tonumber(record[4]),
|
||||
}
|
||||
private.current_record.values = {}
|
||||
for i=5, getn(record) do
|
||||
private.current_record.values[private.current_record.min - 5 + i] = tonumber(record[i])
|
||||
end
|
||||
private.current_item_key = item_key
|
||||
end
|
||||
end
|
||||
|
||||
function private.write_current_record()
|
||||
local data = private.load_data()
|
||||
|
||||
local values = {}
|
||||
for i=private.current_record.min,private.current_record.max do
|
||||
tinsert(values, private.current_record.values[i])
|
||||
end
|
||||
|
||||
data.item_data[private.current_item_key] = Aux.persistence.serialize({
|
||||
private.current_record.min,
|
||||
private.current_record.max,
|
||||
private.current_record.step,
|
||||
private.current_record.count,
|
||||
Aux.persistence.serialize(values, ':'),
|
||||
}, ':')
|
||||
end
|
||||
|
||||
function public.get_price_data(item_key)
|
||||
private.read_current_record(item_key)
|
||||
|
||||
local median = 0
|
||||
local Q1 = 0
|
||||
local Q3 = 0
|
||||
local percent40 = 0
|
||||
local percent30 = 0
|
||||
local recount = 0
|
||||
|
||||
if private.current_record.min == private.current_record.max then
|
||||
median = private.current_record.min * private.current_record.step
|
||||
else
|
||||
for i = private.current_record.min, private.current_record.max do
|
||||
recount = recount + private.current_record.values[i]
|
||||
if Q1 == 0 and private.current_record.count > 4 then -- Q1 is meaningless with very little data
|
||||
if recount >= private.current_record.count / 4 then
|
||||
Q1 = i * private.current_record.step
|
||||
end
|
||||
end
|
||||
if percent30 == 0 then
|
||||
if recount >= private.current_record.count * 0.3 then
|
||||
percent30 = i * private.current_record.step
|
||||
end
|
||||
end
|
||||
if percent40 == 0 then
|
||||
if recount >= private.current_record.count * 0.4 then
|
||||
percent40 = i * private.current_record.step
|
||||
end
|
||||
end
|
||||
if median == 0 then
|
||||
if recount >= private.current_record.count / 2 then
|
||||
median = i * private.current_record.step
|
||||
end
|
||||
end
|
||||
if Q3 == 0 and private.current_record.count > 4 then -- Q3 is meaningless with very little data
|
||||
if recount >= private.current_record.count * 3 / 4 then
|
||||
Q3 = i * private.current_record.step
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return median, Q1, Q3, percent30, percent40, private.current_record.count, private.current_record.step
|
||||
end
|
||||
|
||||
function public.process_auction(auction_info)
|
||||
|
||||
if auction_info.buyout_price == 0 then
|
||||
return
|
||||
end
|
||||
|
||||
private.read_current_record(auction_info.item_key)
|
||||
|
||||
local buyout = auction_info.buyout_price / auction_info.aux_quantity
|
||||
|
||||
if private.current_record.count == 0 then
|
||||
private.current_record.step = ceil(buyout / 100)
|
||||
end
|
||||
|
||||
local index = ceil(buyout / private.current_record.step)
|
||||
|
||||
if private.current_record.count <= 20 and index > 100 then
|
||||
private.refactor(buyout, 100)
|
||||
index = 100
|
||||
end
|
||||
|
||||
if private.current_record.count <= 20 or index <= 300 then
|
||||
|
||||
if private.current_record.min == 0 then
|
||||
private.current_record.min = index
|
||||
private.current_record.max = index
|
||||
private.current_record.values[index] = 0
|
||||
elseif private.current_record.min > index then
|
||||
for i = index, private.current_record.min - 1 do
|
||||
private.current_record.values[i] = 0
|
||||
end
|
||||
private.current_record.min = index
|
||||
elseif private.current_record.max < index then
|
||||
for i = private.current_record.max + 1, index do
|
||||
private.current_record.values[i] = 0
|
||||
end
|
||||
private.current_record.max = index
|
||||
end
|
||||
|
||||
private.current_record.values[index] = private.current_record.values[index] + 1
|
||||
private.current_record.count = private.current_record.count + 1
|
||||
|
||||
local median = public.get_price_data(auction_info.item_key)
|
||||
|
||||
local step_too_small = private.current_record.step < median / 115
|
||||
local step_too_large = private.current_record.step > median / 85 and private.current_record.step > 1
|
||||
if private.current_record.count > 20 and (step_too_small or step_too_large) then
|
||||
private.refactor(median, 100)
|
||||
end
|
||||
|
||||
private.write_current_record()
|
||||
end
|
||||
end
|
||||
|
||||
function private.refactor(pmax, precision)
|
||||
|
||||
local new_step = ceil(pmax / precision)
|
||||
|
||||
if private.current_record.min == 0 then
|
||||
return
|
||||
end
|
||||
|
||||
local conversion = private.current_record.step / new_step
|
||||
local new_min = ceil(conversion * private.current_record.min)
|
||||
local new_max = ceil(conversion * private.current_record.max)
|
||||
local new_values = {}
|
||||
|
||||
if new_max > 300 then
|
||||
--we need to crop off the top end
|
||||
new_max = 300
|
||||
private.current_record.max = floor(300 / conversion)
|
||||
end
|
||||
for i = new_min, new_max do
|
||||
new_values[i] = 0
|
||||
end
|
||||
local new_count = 0
|
||||
for i = private.current_record.min, private.current_record.max do
|
||||
local j = ceil(conversion * i)
|
||||
new_values[j] = new_values[j] + private.current_record.values[i]
|
||||
new_count = new_count + private.current_record.values[i]
|
||||
end
|
||||
|
||||
private.current_record.min = new_min
|
||||
private.current_record.max = new_max
|
||||
private.current_record.step = new_step
|
||||
private.current_record.count = new_count
|
||||
private.current_record.values = new_values
|
||||
end
|
||||
Reference in New Issue
Block a user