postgresql 如何运行postgres查询?

h43kikqp  于 2022-11-04  发布在  PostgreSQL
关注(0)|答案(2)|浏览(197)

我希望构建一个筛选器组件,其中我的搜索内容类似于b_cycle_type = '1st Day Of The Month'
而在数据库中,b_cycle_type存储为-1,0,1,2,3,4,5
如何准备postgres语句?
我在努力

SELECT "customers".* FROM "customers" WHERE (CASE customers.b_cycle_type
                            WHEN -1 THEN 'Last day of the month'
                            WHEN 0 THEN 'Align with first'
                            ELSE
                              to_char(customers.b_cycle_type, '99th') || ' Day Of The Month'
                            END = '27th Day Of The Month')

它没有返回我任何结果。

jfewjypa

jfewjypa1#

这部分to_char(customers.b_cycle_type, '99th')实际上会导致' 27th'(to_char Docs [* 从底部开始第6个]),因此为了解决这个问题,我将使用TRIM函数。

CREATE TABLE customers(
   id SERIAL PRIMARY KEY, 
   b_cycle_type INT);
INSERT INTO customers(b_cycle_type)
SELECT * FROM generate_series(-1,30);

SELECT "customers".*
FROM "customers"
WHERE 
  CASE b_cycle_type
   WHEN -1 THEN 'Last day of the month'
   WHEN 0 THEN 'Align with first'
   ELSE
     TRIM(to_char(b_cycle_type, '99th')) || ' Day Of The Month'
 END = '27th Day Of The Month'

范例
您可以避免使用原始SQL,但这并不好

your_variable = '27th Day Of The Month'
customer_table = Customer.arel_table 
case_stmt = Arel::Case.new(customer_table[:b_cycle_type])
              .when(-1).then(Arel.sql("'Last day of the month'"))
              .when(0).then(Arel.sql("'Align with first'"))
              .else(
                 Arel::Nodes::InfixOperation.new('||'
                   Arel::Nodes::NamedFunction.new('TRIM',[
                     Arel::Nodes::NamedFunction.new('to_char',
                       [customer_table[:b_cycle_type],Arel.sql("'99th'")])
                   ]),
                   Arel.sql("' Day Of The Month'")
                 )
              )
Customer.where(case_stmt.eq(your_variable))
jv4diomz

jv4diomz2#

SELECT "customers".* 
FROM "customers" 
WHERE (CASE b_cycle_type
         WHEN -1 THEN 'Last day of the month'
         WHEN 0 THEN 'Align with first'
         ELSE 
           CASE 
              WHEN "customers".b_cycle_type BETWEEN -1 AND 31 
              THEN trim(to_char("customers".b_cycle_type,'99th')||' Day Of The Month')
           END
      END = '27th Day Of The Month');

但是:
1.如果b_cycle_type列是一个日期列,则应该将该列定义为date类型,而不是数值类型。它将使您能够简单地执行where extract('day' from b_cycle_type) = 27操作。它还将负责验证任何人试图插入到表中的所有数据,而不必维护自定义触发器和约束。
1.如果出于某种原因必须将其设置为日偏移量,则应将其设置为smallintdecimal(2,0)。另外,将其对应的实际日期保存为单独的列,以便能够轻松地计算不同长度的月份,以及二月较长时的闰年。
1.如果不能改变"customers"表的结构,则无论何时处理该表中的数据,都应该确保b_cycle_type介于-1和31之间,并且在给定年份中给定月份的可能天数范围内。

相关问题