我的 idea 是:

服务器:安装了最新MariaDB的Ubuntu

这是一种投资组合算法,用户可以购买美元等货币的股票,但他的投资组合可以是欧元,所以必须转换价值.

  1. 我需要一个接近创建日期的汇率,如果不使用从日期之前的汇率.
  2. 将AMOMENTS_LEFTS*PRICE转换为我想要的货币的总和(在本例中,为便于理解,它将是1的汇率,在本例中,目标货币将提交OVER查询.
  3. 结果应该除以金额的总和_左,以获得正确的购买,也就是AVG的价格.

我更新了数据以使测试变得更简单,比如源货币现在与目标货币相同,因此计算是1:1

SQL Fiddle is here: http://sqlfiddle.com/#!9/8c7fc59/11
Results running against my DB with querys 

    https://pastebin.com/pSerHN0j

前两个结果是我想要的,第三个.一个是来自jmvCollaborator的,其中avg的购买是正确的,但金额翻了一番.

SQL Export with more Data 

    https://pastebin.com/d1aVX2wm

更新问题:

胜于子查询的解决方案是有效的,但这种方法在性能上不是最好的,所以我目前正在寻找没有它的解决方案.

在我的信息分区后,这里应该有一个解决方案,但这不是我的那种知识,所以也许有人可以在这里帮助我.

推荐答案

我会在这里写下一些发现,首先我想再次判断您的第一个查询是否有效,请确认:

SELECT SUM(amounts_left*price)/SUM(amounts_left) as eBuyIN
 FROM transactions as t 
 WHERE 1 GROUP BY currency_id,broker_id,portfolio_id,instrument_id; 

如果它不工作,那么让我分享一些关于我们工作的查询的发现,即:

SELECT 
    SUM(price)/SUM(mleft) 
FROM(
    SELECT
        `instrument_id`,
        amounts_left AS mleft, 
        amounts_left * price * (
             SELECT `rate` 
             FROM `currency_exchanges` 
             WHERE `from_currency_id` = t.currency_id 
               AND `to_currency_id` = 2 
               AND `date` <= t.created 
             ORDER BY `date` DESC LIMIT 1
        ) AS price
    FROM `transactions` AS `t` 
    WHERE `action` = 1 
      AND `portfolio_id` = 128 
) a

查询开销为2.72,因为它由于嵌套查询而执行全表扫描.我自由地使用CTE和Over Partition Bytry 了一种不同的方法,查询成本是0.35非唯一键查找,因为分区内的列比前一个查询要快得多,下面是CTE代码:

WITH 
cte AS (
SELECT ROW_NUMBER() OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id ORDER BY amounts_left DESC
        ) AS rowNumber,        
       SUM(amounts_left) OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id
       ORDER BY amounts_left DESC ROWS BETWEEN CURRENT ROW AND 1 FOLLOWING) AS amountsleftT,       
       SUM(amounts_left*price) OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id
       ORDER BY amounts_left DESC ROWS BETWEEN CURRENT ROW AND 1 FOLLOWING) AS priceT
FROM currency_exchanges AS ce
JOIN transactions AS t
ON from_currency_id = t.currency_id 
AND to_currency_id = 2 
AND ce.date <= t.created
AND action = 1 and portfolio_id = 128 
)
Select priceT/amountsleftT as Total from cte where rowNumber = 1;

我建议添加更多的数据,这样就可以测试许多不同的 case ,您可以继续在小提琴上工作,分享链接.

希望我能在某种程度上帮上忙.

由于聚合错误,更新了UPDATE个带有Over Partition by的查询.IMPORTANT:尽管如此,性能仍然比其他方法更好. 以下是正在运行的查询:

WITH cte AS
(
select 
instrument_id,
ROW_NUMBER() OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id) AS rowNumber,
Sum(amounts_left* price *ce.rate) OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id) AS priceSum,
Sum(amounts_left) OVER(PARTITION BY t.currency_id,t.broker_id,t.portfolio_id,t.instrument_id) amountsleftSum 
from transactions t left join
     (select ce.*, row_number() over (partition by from_currency_id order by date desc) as seqnum
      from currency_exchanges ce
      where
         to_currency_id = 2     
      order by ce.date desc
     ) ce
     on ce.from_currency_id = t.currency_id and seqnum = 1
  WHERE 
    ce.date <= t.created 
    AND action = 1 AND amounts_left > 0 AND portfolio_id = 128 
    
)    
SELECT     
 priceSum/amountsleftSum as   eBuyIN,
       amountsleftSum AS amounts_left,
       instrument_id       
 FROM cte
 WHERE  rownumber = 1; 

Sql相关问答推荐

帮助修复查询以识别SQL DW中数据中的递归关系

如何在SQL Server中列出从当前月份开始的过go 10年中的月份

SQL查询视图与连接?

删除MariaDB数据库中的JSON数据

SQL将 Select 查询作为新列添加到另一个 Select 查询

BigQuery-当子查询不返回任何结果时,所有结果为零

使用DatePart函数对日期时间值进行分组

从数据库中查找总和大于或等于查询中的数字的数字

如何使用SQL Server中的Nodes()方法执行与OPENXML相同的操作

如何使用SQL生成数据的滚动3天总和

在同一列上迭代时计算持续时间

GRAFANA 数据库查询错误:pq:列名称不存在

SQL 查询是否返回列表中仅包含某些值而不包含其他值的行?

在SQL中实现表格数据透视类型报表

如何为给定的股票数据集计算利润/亏损,确保先卖出先买入的股票

查询以查找今天和昨天的数据之间的差异以及伪列

如何将 CONCATENATED 值与临时表中的值匹配

如何计算每行出现的次数并显示在另一个表中?

每组跨行曲折?

交叉应用 OPENJSON / PIVOT - 错误的顺序