【问题标题】:How to sort values in columns and update table?如何对列中的值进行排序并更新表?
【发布时间】:2012-04-22 05:05:33
【问题描述】:

我对 sql 完全陌生,我自己做不到。所以我需要你的帮助。 我想对列中的值进行排序,然后保存更改。但我不知道该怎么做。

表格是这样的:

Id | Name | SomeDescription
---------------------------
1  |Best  | Description1
2  |Worth | Description2
3  |Good  | Description3

我想得到类似的东西:

Id | Name | SomeDescription
---------------------------
1  |Best  | Description1
2  |Good  | Description3
3  |Worth | Description2

所以我需要对“id”和“name”列进行排序。

我使用以下语句对“名称”列的值进行排序:

SELECT * FROM games ORDER BY name ASC

但是如何对 id 列的值进行排序并将更改保存在表中? 请帮忙。

【问题讨论】:

  • 一般排序时不会更改数据,数据表从不保证按特定顺序返回数据。
  • 为什么要保存已排序的数据库表?
  • @MarioDeSchaepmeester 历史悠久。简而言之,我的应用程序需要它。
  • 我认为没有一种方法可以有效地对数据库表进行排序,而无需将已排序的表保存为副本或使用非常复杂或一系列更新语句。最好的办法是编写一个存储过程 或保存对表进行排序的查询。这样你只需要执行它来获取排序表。你不会那样弄乱你的数据库。我仍然可以看到它已排序的 reading 值,但将其保存已排序是没有意义的。所以我的意思是你应该“保存排序后的阅读”。

标签: sql


【解决方案1】:

您将不得不使用第二张桌子

  1. 创建一个与games 表结构相同的新表games2,确保ID 是自动递增的

    CREATE TABLE `games2` LIKE `games`;
    
  2. 将排序后的数据复制到games2

    INSERT INTO `games2` (`Name`, `SomeDescription`) SELECT `Name`, `SomeDescription` FROM `games` ORDER BY `Name`
    
  3. 删除或移动旧表

    -- DROP TABLE `games`;
    -- or
    RENAME TABLE `games` TO `games1`;
    
  4. 将新表重命名为旧名称

    RENAME TABLE `games2` TO `games`;
    

这些步骤将产生您想要的结果。

【讨论】:

  • @Sabre & Umbrella 表实现/存储有顺序,但表是无序的抽象。在查询中获得顺序的唯一方法是最外层的 ORDER BY。
  • 这怎么这么受欢迎?如果表有一个自动生成的 PK,那么这段代码可能会用 PK 顺序(最初)与Name 列的排序一致的表替换原始表,但 SQL 对表本身没有排序意义,只有排序 结果.
  • 它准确地回答了这个问题。您描述的问题是问题,提问者试图做一些我们通常不做的事情——重新排列磁盘上的行。我想不出一个用例,因为我们都只是在我们的结果集上使用ORDER BY,但是,这显然是问题所在,这就是你的做法。
【解决方案2】:

您可以使用 ROW_NUMBER 排名函数对行重新编号。

SELECT UnsortedId = id
, SortedId = ROW_NUMBER() OVER (ORDER BY g.name, g.id)
FROM games 

【讨论】:

    【解决方案3】:

    你可以使用更简单的alter table命令。

    mysql> ALTER TABLE games ORDER BY name asc;
    

    就是这样!

    【讨论】:

    • 也许这适用于 mysql,但绝对不适用于 t-sql。会很方便!
    【解决方案4】:

    这很简单。只需使用一些代码。我已经尝试过了,它正在工作。首先创建一个临时表,同时对值进行排序。

        create table new as select * from games order by name;
    

    然后使用,

        drop table games;
    

    现在使用与 new 相同的属性和数据再次创建游戏桌(此处排序是可选的)使用,

        create table games as select * from new order by name;
    

    现在删除临时表'new'

        drop table new;
    

    现在检查你的桌子。必须解决。

    【讨论】:

      【解决方案5】:

      您可以同时对两个字段进行排序。

      SELECT *
      FROM games
      ORDER BY id DESC, name ASC
      

      我不明白你在表格中保存更改是什么意思。 ORDER BY 只是更改您正在查看的显示,它不会更改表中的数据,除非您执行 UPDATE

      如果你对 SQL 不熟悉,网上有很多教程可以帮助你:

      SQL Course

      Beginner SQL Tutorial

      SQL Tutorial - Learn SQL

      根据 cmets 进行编辑,一步完成:

      create table #temp
      (
          id int,
          name varchar(50),
          somedesc varchar(50)
      )
      
      insert into #temp values (1, 'best', 'desc1')
      insert into #temp values (2, 'worth', 'desc2')
      insert into #temp values (3, 'good', 'desc3')
      
      update t1
      SET t1.id = t2.rn
          , t1.somedesc = t1.somedesc
      FROM #temp t1
      JOIN 
      (
          select id, name, somedesc, row_number() over(order by name, id) as rn
          from #temp 
      ) t2
      on t1.id = t2.id
      
      select *
      from #temp
      order by id
      
      drop table #temp
      

      【讨论】:

      • 您说的当然是正确的,但请注意他在示例中想要完成的操作 - Id 列保持不变。
      • @cha0site 你是对的。当我以这种方式对两个字段进行排序时,表中没有任何变化
      • @cha0site 你是对的,我误解了 OP。我已经更新了我的答案
      【解决方案6】:

      这是我的解决方法...愚蠢的简单:

      1. 提取到临时表

      SELECT SortKeyValue (添加任何其他固定值,只是不包括现有序列) INTO #Temp FROM SourceTable;

      1. 清空表:

      截断表源表

      1. 重新插入:

      INSERT INTO SourceTable (SortKeyValue, DisplayOrder (加上其他字段)) SELECT SortKeyValue, ROW_NUMBER() OVER (ORDER BY SortKeyValue) AS DispOrd (加上其他字段) FROM #Temp;

      1. 完成!

      【讨论】:

        【解决方案7】:

        SQL> 从游戏中选择 * 按 ID、姓名排序;

        【讨论】:

        • 能否请您详细说明您的答案,添加更多关于您提供的解决方案的描述?
        猜你喜欢
        • 1970-01-01
        • 2018-11-06
        • 1970-01-01
        • 1970-01-01
        • 2010-11-18
        • 2019-10-12
        • 2013-07-16
        • 2016-08-03
        • 2022-01-19
        相关资源
        最近更新 更多