这样的 SQL 语句该怎么写

2014-10-17 10:50:39 +08:00
 CosWind
一张表Test,3个字段:a ,b ,score

a ,b字段都有值,score由a / b的值按区段打分, 如大于0.3是5分,大于0.18是4分,大于0.12是3分等

那么问题来了:如何用一条SQL语句达到目的
3878 次点击
所在节点    MySQL
22 条回复
lichao
2014-10-17 10:57:14 +08:00
select a, b, case when a/b > 0.5 then 5 when a/b > 0.3 then 4 when a/b > 0.12 then 3 else 0 end as score
CosWind
2014-10-17 11:11:32 +08:00
@lichao 诶,这样 a/b会算几次?
lichao
2014-10-17 11:13:31 +08:00
@CosWind 最影响数据库性能的是磁盘 IO,数学计算与之相比可忽略不计
tobyzw
2014-10-17 11:17:33 +08:00
select a, b, case when a/b > 0.5 then 5 when a/b > 0.3 then 4 when a/b > 0.12 then 3 else 0 end as score
-------------------------
可能会有问题,a/b可能会出异常,b=0的情况需要考虑进去
CosWind
2014-10-17 11:19:22 +08:00
@lichao 诶。我测试的结果是80w的表,这样写和a/b设置成常量1计算出来的结果所需要的时间分别是1.01s 和 0.85s,差别还是有的
xudshen
2014-10-17 11:19:32 +08:00
用a > 0.5*b 会不会效率高一点?
CosWind
2014-10-17 11:19:41 +08:00
@tobyzw 是的。
CosWind
2014-10-17 11:20:03 +08:00
@xudshen 条件有多个。
CosWind
2014-10-17 11:21:51 +08:00
@lichao 额。。我这测试不科学。
xudshen
2014-10-17 11:24:21 +08:00
@CosWind 你可以把a/b的值存起来,像这样的sql肯定也不是仅仅run一次的,与其每次都计算,不如一次先搞定
CosWind
2014-10-17 11:26:41 +08:00
@xudshen 对,我想要的就是这个效果,a/b的计算只计算一次,但是我想只用一条SQL达成目的
xudshen
2014-10-17 11:28:46 +08:00
@CosWind 在insert的时候就包括a/b,或者设置个insert,update的trigger
frye
2014-10-17 11:43:43 +08:00
SELECT
a,
b,
IF(
a / b > 0.12,
IF(
a / b > 0.18,
IF(
a / b > 0.3,
5,
4
),
3
),
0
) AS score
FROM
table_name
cye3s
2014-10-17 11:50:06 +08:00
子查询查一次a/b,外面套case
frye
2014-10-17 11:52:20 +08:00
INSERT INTO TEST_A (account_id, profit_rate, score) SELECT
account_id,

IF (
init_funds > 0,
profit / init_funds,
0
) AS profit_rate,

IF (

IF (
init_funds > 0,
profit / init_funds,
0
) > 0.12,

IF (

IF (
init_funds > 0,
profit / init_funds,
0
) > 0.18,

IF (

IF (
init_funds > 0,
profit / init_funds,
0
) > 0.3,
5,
4
),
3
),
0
) AS score
FROM
TEST_B
CosWind
2014-10-17 11:55:03 +08:00
@cye3s 子查询性能会不会差一点
CosWind
2014-10-17 11:55:20 +08:00
@frye a/b 能否只算一次呢
frye
2014-10-17 11:57:14 +08:00
INSERT INTO TEST_A (account_id, profit_rate, score) SELECT
TEST_B.account_id,
TEST_B.profit_rate,

IF (
TEST_B.profit_rate > 0.12,

IF (
TEST_B.profit_rate > 0.18,

IF (TEST_B.profit_rate > 0.3, 5, 4),
3
),
0
) AS score
FROM
(
SELECT

IF (
init_funds > 0,
profit / init_funds,
0
) AS profit_rate,
account_id
FROM
TEST_B
) AS TEST_B
CosWind
2014-10-17 12:03:47 +08:00
@frye 这样用子查询,感觉有点得不偿失。
viquuu
2014-10-17 12:05:15 +08:00
select a,b,
case when c > 0.5 then 5 when c > 0.3 then 4 when c > 0.12 then 3 else 0 end as score
from (
select a,b, a/isnull(b,1) as c from test
)

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/139497

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX