按 ID 超过 10000 的字段排序

发布于 2024-11-08 12:06:07 字数 294 浏览 0 评论 0原文

我需要使用按字段排序来进行特定排序。

select * from table order by field(id,3,4,1,2.......upto 10000 ids)

由于所需的排序无法从 SQL 中获取,那么它对性能的影响有多大,是否可行?

评论更新:

  • 排序取决于用户和类别 ID,并且可以是用户想要的任何内容。
  • 订购规格每天都会变化。

因此,我们需要根据用户和类别进行自定义排序,并且该排序需要每天更改。

I need to do specific ordering with use of order by field.

select * from table order by field(id,3,4,1,2.......upto 10000 ids)

As the ordering required is not gettable from SQL then how much it affect as per performance and is it feasible to do?

Updates from the comments:

  • Ordering depends on user and category IDs and can be anything the user wants.
  • The ordering specification changes (about) daily.

So, we need a custom ordering that depends on the user and category and this ordering needs to change daily.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

不必了 2024-11-15 12:06:07

最简单的方法是将您的订单放在一个单独的表中(在本例中称为 ordering_table):

 id | position
----+----------
  1 | 11
  2 | 42
  3 | 23
 etc.

上面的意思是“将 1 的 id 放在位置 11, 2在位置 42,3 在位置 23,...”。然后,您可以将该排序表加入:

SELECT t.id, t.col1, t.col2
FROM some_table t
JOIN ordering_table o ON (t.id = o.id)
ORDER BY o.position

其中 ordering_table 是定义您的奇怪排序的表(如上所述)。这种方法只是将您的排序函数表示为一个表(任何具有有限域的函数本质上只是一个表)。

只要排序表完整,这种“排序表”方法就应该可以正常工作。

如果您只需要在一个地方进行这种奇怪的排序,那么您可以将 position 列合并到主表中,并添加 NOT NULLUNIQUE 约束该列以确保您涵盖所有内容并具有一致的顺序。

进一步的评论表明您希望为不同的用户和类别提供不同的排序,并且排序每天都会发生变化。您可以为每个条件创建单独的表(这会导致组合爆炸),或者按照 Mikael Eriksson 和 ypercube 的建议,在排序表中添加更多列来保存用户和类别:

CREATE TABLE ordering_table (
    thing_id    INT NOT NULL,
    position    INT NOT NULL,
    user_id     INT NOT NULL,
    category_id INT NOT NULL
);

thing_iduser_idcategory_id 将是各自表的外键,您可能希望对 ordering_table 中的所有列建立索引但是花几分钟查看查询计划是值得的,看看索引是否值得使用。您还可以将所有四列设为主键以避免重复。然后,查找查询将如下所示:

SELECT t.id, t.col1, t.col2
FROM some_table t
LEFT JOIN ordering_table o
     ON (t.id = o.thing_id AND o.user_id = $user AND o.category_id = $cat)
ORDER BY COALESCE(o.position, 99999)

其中 $user$cat 分别是用户 ID 和类别 ID。请注意对 LEFT JOIN 的更改以及添加 COALESCE 以允许 ordering_table 中缺少行,这些更改会将订单中没有指定位置的任何内容推送到列表的底部,而不是而不是将它们从结果中完全删除。

The easiest way would be to put your ordering in a separate table (called ordering_table in this example):

 id | position
----+----------
  1 | 11
  2 | 42
  3 | 23
 etc.

The above would mean "put an id of 1 at position 11, 2 at position 42, 3 at position 23, ...". Then you can join that ordering table in:

SELECT t.id, t.col1, t.col2
FROM some_table t
JOIN ordering_table o ON (t.id = o.id)
ORDER BY o.position

Where ordering_table is the table (as above) that defines your strange ordering. This approach simply represents your ordering function as a table (any function with a finite domain is, essentially, just a table after all).

This "ordering table" approach should work fine as long as the ordering table is complete.

If you only need this strange ordering in one place then you could merge the position column into your main table and add NOT NULL and UNIQUE constraints on that column to make sure you cover everything and have a consistent ordering.

Further commenting indicates that you want different orderings for different users and categories and that the ordering will change on a daily basis. You could make separate tables for each condition (which would lead to a combinatorial explosion) or, as Mikael Eriksson and ypercube suggest, add a couple more columns to the ordering table to hold the user and category:

CREATE TABLE ordering_table (
    thing_id    INT NOT NULL,
    position    INT NOT NULL,
    user_id     INT NOT NULL,
    category_id INT NOT NULL
);

The thing_id, user_id, and category_id would be foreign keys to their respective tables and you'd probably want to index all the columns in ordering_table but a couple minutes of looking at the query plans would be worthwhile to see if the indexes get used would be worthwhile. You could also make all four columns the primary key to avoid duplicates. Then, the lookup query would be something like this:

SELECT t.id, t.col1, t.col2
FROM some_table t
LEFT JOIN ordering_table o
     ON (t.id = o.thing_id AND o.user_id = $user AND o.category_id = $cat)
ORDER BY COALESCE(o.position, 99999)

Where $user and $cat are the user and category IDs (respectively). Note the change to a LEFT JOIN and the addition of COALESCE to allow for missing rows in ordering_table, these changes will push anything that doesn't have a specified position in the order to the bottom of the list rather than removing them from the results completely.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文