我可以在 PostgreSQL 中将一堆布尔列转换为单个位图吗?
我想将查询转换为位掩码,例如:
SELECT BoolA, BoolB, BoolC, BoolD FROM MyTable;
转换为位掩码,其中位由上面的值定义。
例如,如果 BoolA
和 BoolD
为 true,我需要 1001
或 9
。
我的想法是:
SELECT
CASE WHEN BoolD THEN 2^0 ELSE 0 END +
CASE WHEN BoolC THEN 2^1 ELSE 0 END +
CASE WHEN BoolB THEN 2^2 ELSE 0 END +
CASE WHEN BoolA THEN 2^3 ELSE 0 END
FROM MyTable;
但我不确定这是否是最好的方法,而且看起来相当冗长。有没有简单的方法可以做到这一点?
I'd like to convert a query such as:
SELECT BoolA, BoolB, BoolC, BoolD FROM MyTable;
Into a bitmask, where the bits are defined by the values above.
For example, if BoolA
and BoolD
were true, I'd want 1001
or 9
.
I have something in mind to the effect of:
SELECT
CASE WHEN BoolD THEN 2^0 ELSE 0 END +
CASE WHEN BoolC THEN 2^1 ELSE 0 END +
CASE WHEN BoolB THEN 2^2 ELSE 0 END +
CASE WHEN BoolA THEN 2^3 ELSE 0 END
FROM MyTable;
But I'm not sure if this is the best approach and seems rather verbose. Is there an easy way to do this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
对于位掩码,类型
bitstring
< /strong> 将是更好的选择。可能看起来像这样:true
转换为1
,false
转换为0
。您可以简单地将位连接到位串。将 bit(n) 转换为整数
似乎您需要一个整数作为结果 - 有一个简单的 &快速方法:
请务必阅读“位字符串函数”一章中的细则和手册的操作员”。
我又提出了两个想法,并用 10k 行进行了快速测试/参考,以总结所有内容。
测试设置:
演示:
您还可以使用
|
(按位 OR)代替+
运算符。单独的测试运行显示所有五种方法的性能基本相同。
For a bitmask, the type
bitstring
would be the better choice. Could look like this then:true
converts to1
,false
to0
. You can simply concatenate bits to a bitstring.Cast bit(n) to integer
It seems you need an
integer
as result - there is a simple & fast way:Be sure to read the fine print in the chapter "Bit String Functions and Operators" of the manual.
I came up with two more ideas and put together a quick test / reference with 10k rows to sum it all up.
Test setup:
Demo:
You could also use
|
(bitwise OR) instead of the+
operator.Individual test runs show basically the same performance for all five methods.
也许是这样的:
其中
<<
是按位左移
运算符。Maybe like this:
where
<<
is thebitwise shift left
operator.我也想出了这个方法。这是我能找到的最简洁的,除了编写自定义函数之外。我会接受这个答案,除非有人有更聪明的东西。
I came up with this approach as well. It's the most concise I could find short of writing a custom function. I'll accept this answer unless anyone has anything more clever.