最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

一文詳解小白也能懂的SQL高效去重技巧

 更新時間:2025年07月06日 09:37:47   作者:一勺菠蘿丶  
當你的數(shù)據(jù)中有重復記錄時,如何快速找到每個分組的最新一條,一個優(yōu)雅的SQL查詢就能解決,下面小編就來和大家詳細講解一下SQL高效的去重技巧吧

生活中的例子

想象你管理一家網(wǎng)店,同一個訂單(order_number)中的同一商品(product)可能有多次更新記錄(比如庫存變化、價格調(diào)整)。你只想查看每個訂單商品的最新狀態(tài),這時就需要用到"分組取最新記錄"的操作。

原理解析:給數(shù)據(jù)分組并編號

SELECT
  *,
  ROW_NUMBER() OVER (
    PARTITION BY order_number, product, craft, trade_name 
    ORDER BY create_time DESC
  ) AS rn
FROM client_product

這個查詢的核心是ROW_NUMBER()函數(shù),它像老師給學生排隊一樣:

  • 分組(PARTITION BY):把相同訂單+產(chǎn)品+工藝+貿(mào)易名稱的記錄分成一組
  • 排序(ORDER BY):每組內(nèi)按創(chuàng)建時間倒序排列(最新時間排第一)
  • 編號(rn):給每組內(nèi)的記錄標記序號(1,2,3…)

完整查詢解析

SELECT *
FROM (
  -- 步驟1:給所有記錄標記組內(nèi)序號
  SELECT *,
    ROW_NUMBER() OVER (
      PARTITION BY order_number, product, craft, trade_name 
      ORDER BY create_time DESC
    ) AS rn
  FROM client_product
  WHERE 
    production_order_number IS NOT NULL  -- 排除生產(chǎn)訂單號為空
    AND order_number IS NOT NULL         -- 排除訂單號為空
    AND craft != ''                      -- 排除工藝為空
    AND del_flag = '0'                   -- 只取未刪除記錄
    AND deliver_status != '0'            -- 排除未交付狀態(tài)
) AS ranked
-- 步驟2:只取每組最新記錄
WHERE rn = 1

關(guān)鍵步驟拆解

1.數(shù)據(jù)過濾(WHERE)

只處理有效數(shù)據(jù):非空訂單號、有生產(chǎn)訂單號、工藝不為空、未刪除、已交付

2.分組標記(ROW_NUMBER)

訂單號產(chǎn)品創(chuàng)建時間組內(nèi)序號(rn)
A1001手機殼2023-01-051(最新)
A1001手機殼2023-01-032
B2002數(shù)據(jù)線2023-01-041(最新)

3.篩選結(jié)果(WHERE rn=1)

只保留每組中rn=1的記錄,即每個組合的最新數(shù)據(jù)

實際應用場景

  • 訂單管理:獲取每個訂單的最新狀態(tài)
  • 設備監(jiān)控:讀取每個傳感器的最新讀數(shù)
  • 用戶行為:提取每個用戶最近一次登錄記錄
  • 價格跟蹤:查看每個商品的最新定價

性能小貼士

當數(shù)據(jù)量很大時:

  • order_number, product, craft, trade_name上創(chuàng)建索引
  • create_time上創(chuàng)建降序索引
  • 定期清理歷史數(shù)據(jù)

方法補充

以下是幾種去重的SQL寫法

在 SQL 中,數(shù)據(jù)去重有多種實現(xiàn)方式,以下是幾種常見寫法及其適用場景:

1. 使用 DISTINCT 關(guān)鍵字

語法:

SELECT DISTINCT column1 [, column2, ...]  
FROM table_name;  

說明:直接對指定字段組合進行唯一性篩選,僅保留首次出現(xiàn)的記錄。

示例:

SELECT DISTINCT address FROM student; -- 獲取不重復的地址  

局限性:

  • 若對多字段去重,需所有字段值完全相同才視為重復。
  • 無法同時返回非去重字段的原始值,僅能展示去重字段。

2. 使用 GROUP BY 子句

語法:

SELECT column1 [, aggregate_function(column2), ...]  
FROM table_name  
GROUP BY column1 [, column2, ...];  

說明:按指定字段分組,結(jié)合聚合函數(shù)(如 MAX、MINCOUNT 等)獲取其他字段信息。
示例:

SELECT MIN(id), address FROM student GROUP BY address; -- 按地址去重,返回每組最小 id  

注意:非聚合字段可能來自不同記錄,導致數(shù)據(jù)邏輯上不一致(如不同 id 對應同一 address 時,聚合函數(shù)外的字段取值無明確規(guī)律)。

3. 使用窗口函數(shù)(如 ROW_NUMBER()

語法:

SELECT *  
FROM (  
    SELECT *, ROW_NUMBER() OVER (PARTITION BY column1 ORDER BY column2) AS rn  
    FROM table_name  
) AS t  
WHERE rn = 1;  

說明:先按 PARTITION BY 分組,再按 ORDER BY 排序并生成行號,篩選行號為 1 的記錄。

示例:

SELECT id, name, address  
FROM (  
    SELECT *, ROW_NUMBER() OVER (PARTITION BY address ORDER BY id ASC) AS rn  
    FROM student  
) AS a  
WHERE a.rn = 1; -- 按地址去重,保留每組 id 最小的記錄  

優(yōu)勢:可精準控制保留哪條記錄(如按時間、ID 排序取最新或最舊),但低版本 MySQL 不支持窗口函數(shù)。

4. 使用 IN 子查詢

語法:

SELECT *  
FROM table_name  
WHERE id IN (SELECT MAX(id) FROM table_name GROUP BY column1);  

說明:通過子查詢找到每組唯一標識字段(如自增 id)的最大值,再篩選主表中對應記錄。

示例:

SELECT * FROM student WHERE id IN (SELECT MAX(id) FROM student GROUP BY address); -- 按地址去重,取每組最大 id 的記錄  

適用場景:表中存在唯一標識字段(如 id),且需保留特定條件(如最大 / 最小 id)的記錄。

5. 使用 NOT EXISTS

語法:

SELECT a.*  
FROM table_name a  
WHERE NOT EXISTS (  
    SELECT 1 FROM table_name b  
    WHERE a.column1 = b.column1 AND a.id < b.id  
);  

示例:

SELECT a.* FROM student a WHERE NOT EXISTS (SELECT 1 FROM student b WHERE a.address = b.address AND a.id < b.id); -- 按地址去重,保留每組 id 最大的記錄  

邏輯:對于每一行 a,若不存在 b 行(同 column1 且 id 更大),則保留 a

6. 使用 UNION 去重

語法:

SELECT column1 [, column2, ...]  
FROM table_name1  
UNION  
SELECT column1 [, column2, ...]  
FROM table_name2;  

說明:合并多個查詢結(jié)果并自動去重(UNION ALL 保留全部記錄,不進行去重)。

示例:

SELECT address FROM student UNION SELECT address FROM teacher; -- 合并兩表地址并去重  

注意:大數(shù)據(jù)量時效率較低,建議先用 UNION ALL 再結(jié)合其他方法去重。

7. 使用 INNER JOIN + GROUP BY

語法:

SELECT a.*  
FROM table_name a  
INNER JOIN (  
    SELECT column1, MAX(id) AS max_id  
    FROM table_name  
    GROUP BY column1  
) b ON a.column1 = b.column1 AND a.id = b.max_id;  

示例:

SELECT a.* FROM student a  
INNER JOIN (SELECT address, MAX(id) AS max_id FROM student GROUP BY address) b  
ON a.address = b.address AND a.id = b.max_id; -- 按地址去重,取每組最大 id 的記錄  

邏輯:先通過子查詢獲取每組最大 id,再與主表關(guān)聯(lián)篩選。

實際應用中,可根據(jù)數(shù)據(jù)庫特性(如是否支持窗口函數(shù))、數(shù)據(jù)規(guī)模、業(yè)務需求(如保留特定記錄)選擇合適的方法。例如,簡單單字段去重優(yōu)先用 DISTINCT;需保留其他字段且數(shù)據(jù)一致性要求不高時用 GROUP BY;需精準控制保留記錄時用窗口函數(shù)或 IN/NOT EXISTS 等。

總結(jié)

這個查詢就像給每個分組內(nèi)的記錄按時間倒序排隊,然后只取排在第一位的記錄

通過這個技巧,你可以輕松地從重復數(shù)據(jù)中提取最新記錄,讓數(shù)據(jù)清洗和分析變得更高效!下次遇到類似需求時,不妨試試這個強大的ROW_NUMBER()函數(shù)吧!

(注:實際使用時需根據(jù)業(yè)務需求調(diào)整分組字段和排序規(guī)則)

到此這篇關(guān)于一文詳解小白也能懂的SQL高效去重技巧的文章就介紹到這了,更多相關(guān)SQL去重內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • MySQL?如何將查詢結(jié)果導出到文件(select?…?into?Statement)

    MySQL?如何將查詢結(jié)果導出到文件(select?…?into?Statement)

    我們經(jīng)常會遇到需要將SQL查詢結(jié)果導出到文件,以便后續(xù)的傳輸或數(shù)據(jù)分析的場景,本文就MySQL中select…into的用法進行演示,感興趣的朋友跟隨小編一起看看吧
    2024-08-08
  • MySQL中where?1=1方法的使用及改進

    MySQL中where?1=1方法的使用及改進

    這篇文章主要介紹了MySQL中where?1=1方法的使用及改進,文章主要通對where?1?=?1的使用及改進展開詳細的內(nèi)容介紹,具有一定的參考價值,需要的小伙伴可以參考一下
    2022-05-05
  • 從索引到架構(gòu)的MySQL大表查詢優(yōu)化實戰(zhàn)指南

    從索引到架構(gòu)的MySQL大表查詢優(yōu)化實戰(zhàn)指南

    在MySQL實際開發(fā)中,大表查詢慢是最常見、最頭疼的性能問題,本文將從索引優(yōu)化、SQL優(yōu)化、架構(gòu)優(yōu)化、配置優(yōu)化四個維度出發(fā),結(jié)合可復現(xiàn)的實戰(zhàn)SQL、原理分析、避坑指南,給出一套全鏈路的大表查詢優(yōu)化方案,幫你把性能提升100倍以上
    2026-03-03
  • SQL實戰(zhàn)之行列互轉(zhuǎn)

    SQL實戰(zhàn)之行列互轉(zhuǎn)

    本文介紹了在Hive中進行行轉(zhuǎn)列的幾種方法,包括使用CASE?WHEN/IF、Get_Json_Object、Str_To_Map以及UNION?ALL和EXPLODE函數(shù),每種方法都有其適用場景,感興趣的可以了解一下
    2024-12-12
  • mysql表物理文件被誤刪的解決方法

    mysql表物理文件被誤刪的解決方法

    最近因為失誤不小心誤刪了mysql表的物理文件,這個時候該怎么辦呢?然后抓緊從網(wǎng)上找解決的方法,終于解決了,現(xiàn)在將解決的方法及過程分享給大家,有需要的朋友們可以參考借鑒,感興趣的朋友們下面來一起學習學習吧。
    2016-11-11
  • Mysql數(shù)據(jù)庫之主從分離實例代碼

    Mysql數(shù)據(jù)庫之主從分離實例代碼

    本篇文章主要介紹了Mysql數(shù)據(jù)庫之主從分離實例代碼,MySQL數(shù)據(jù)庫設置讀寫分離,可以使對數(shù)據(jù)庫的寫操作和讀操作在不同服務器上執(zhí)行,提高并發(fā)量和相應速度。
    2017-03-03
  • MySQL的子查詢及相關(guān)優(yōu)化學習教程

    MySQL的子查詢及相關(guān)優(yōu)化學習教程

    這篇文章主要介紹了MySQL的子查詢及相關(guān)優(yōu)化學習教程,使用子查詢時需要注意其對數(shù)據(jù)庫性能的影響,需要的朋友可以參考下
    2015-11-11
  • MySQL中的快照讀和當前讀用法

    MySQL中的快照讀和當前讀用法

    快照讀不加鎖,讀事務開始時的數(shù)據(jù)快照,確保一致性;當前讀加鎖,讀最新數(shù)據(jù),用于更新及鎖定操作,兩者在RC和RR隔離級別下表現(xiàn)不同,MVCC機制支持快照讀,而加鎖機制保障當前讀的數(shù)據(jù)一致性
    2025-08-08
  • CentOS6.4上使用yum安裝mysql

    CentOS6.4上使用yum安裝mysql

    這篇文章主要為大家詳細介紹了CentOS6.4上使用yum安裝mysql圖文教程,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2016-10-10
  • Mysql的語句生成后門木馬的方法

    Mysql的語句生成后門木馬的方法

    這篇文章主要介紹了Mysql的語句生成后門木馬的方法,大家不要隨意搞破壞哦,小伙伴們學習下就好了。
    2015-04-04

最新評論

调兵山市| 富顺县| 美姑县| 海安县| 亳州市| 沽源县| 江油市| 乾安县| 钟山县| 开封县| 始兴县| 精河县| 独山县| 高青县| 叶城县| 仙居县| 明水县| 来安县| 阿尔山市| 叙永县| 惠水县| 淳化县| 迁西县| 穆棱市| 女性| 定日县| 盐池县| 遂昌县| 台湾省| 哈密市| 乾安县| 海门市| 炎陵县| 雅江县| 西青区| 滁州市| 平原县| 郸城县| 汝阳县| 兴文县| 色达县|