Tento článek je zrcadlovým článkem o strojovém překladu, klikněte zde pro přechod na původní článek.

Pohled: 13193|Odpověď: 0

[Tipy] Porovnejte výkon primárního klíče pole Guid pomocí samoinkrementálního pole v knihovně

[Kopírovat odkaz]
Zveřejněno 26.10.2015 9:37:04 | | | |
1. Přehled:

V našem návrhu databáze je primární klíč databáze zásadní a návrh primárního klíče má velký vliv na návrh celé databáze. Porovnám výkon automaticky inkrementálních polí a Guid polí, vítejte k diskusi.

2. Úvod:

1. Samoinkrementální pole

      Samoinkrementální pole se postupně zvyšují pokaždé, což zajišťuje, že primární klíče v tabulce se neopakují. Pokud není překročena a zvyšována maximální hodnota samopřirůstajícího typu pole od začátku, je to téměř nemožné. Je velmi jednoduché použít samoinkrementální pole jako primární klíče, obecně pouze deklarovat samoinkrementující atributy při tvorbě tabulky.

      Samoinkrementální hodnoty jsou všechny globální datové hodnoty, které je třeba v systému udržovat, a hodnota se zvyšuje pokaždé, když jsou data vložena. V současném prostředí, kde ekvivalent generuje jedinečnou identitu, musí být každá přírůstková hodnota uzamčena a odemčena touto globální hodnotou, aby byla zajištěna jedinečnost přírůstku. To může být souběžné úzké hrdlo, které zahrnuje určité výkonnostní problémy.

Při migraci nebo importu dat mohou být samoinkrementální pole duplikována, což je bezpochyby noční můra (už jsem tím trpěl).

      Pokud chcete vytvořit distribuovanou databázi, toto samoinkrementální pole je problém. Je to proto, že v distribuované databázi mohou být tabulky se stejným názvem z různých databází potřeba replikovat synchronně. Samoinkrementální hodnota databázové tabulky je pravděpodobně zdvojena se samoinkrementální hodnotou téže tabulky v jiné databázi.

2. pole uniqueidentifier (Guid)

V databázích MS SQL lze strukturu tabulky vytvořit zadáním typu pole jako uniqueidentifier a její výchozí hodnotu lze generovat pomocí NewID() pro vytvoření unikátního Guid (Globally Unique Identifier).

Guid:指在一台机器上生成的数字,它保证对在同一时空中的所有机器都是唯一的,其算法是通过以太网卡地址、纳秒级时间、芯片ID码和许多可能的数字生成。其格式为:04755396-9A29-4B8C-A38D-00042C1B9028.

Výhodou GUID je, že generované ID je relativně jedinečné, ať už jde o export dat nebo vývoj krok za krokem, nebudou žádné problémy. Nicméně ID, které generuje, je poměrně dlouhé a databázový prostor je také obsazený, takže není třeba to zvažovat, protože cena externího úložiště klesá. Navíc Guid není snadné si zapamatovat, a v tomto ohledu není tak dobrý jako automatická inkrementální pole, což není příliš pohodlné při ladění programů.

3. Testování:

1. Otestujte prostředí

Operační systém: Windows Server 2003 R2 Enterprise Edition Service Pack 2

Databáze: MS SQL 2005

CPU:Intel(R) Pentium(R) 4 CPU 3.40GHz

Paměť: DDRII. 667 1G

Pevný disk: WD 80G

2. Databázové skripty
  1. --自增量字段表
  2. CREATE TABLE [dbo].[Table_Id](
  3.     [Id] [int] IDENTITY(1,1) NOT NULL,
  4.     [Value] [varchar](50) COLLATE Chinese_PRC_CI_AS NULL,
  5. CONSTRAINT [PK_Table_Id] PRIMARY KEY CLUSTERED
  6. (
  7.     [Id] ASC
  8. )WITH (IGNORE_DUP_KEY = OFF) ON [PRIMARY]
  9. ) ON [PRIMARY]

  10. GO
  11. --Guid字段表
  12. CREATE TABLE [dbo].[Table_Guid](
  13.     [Guid] [uniqueidentifier] NOT NULL CONSTRAINT [DF_Table_Guid_Guid]  DEFAULT (newid()),
  14.     [Value] [varchar](50) COLLATE Chinese_PRC_CI_AS NULL,
  15. CONSTRAINT [PK_Table_Guid] PRIMARY KEY CLUSTERED
  16. (
  17.     [Guid] ASC
  18. )WITH (IGNORE_DUP_KEY = OFF) ON [PRIMARY]
  19. ) ON [PRIMARY]

  20. GO
Kopírovat kód
Testovací kód
  1. 1using System;
  2.   2using System.Collections.Generic;
  3.   3using System.Text;
  4.   4using System.Data.SqlClient;
  5.   5using System.Diagnostics;
  6.   6using System.Data;
  7.   8namespace GuidTest
  8.   9{
  9.    class Program
  10.    {
  11.        string Connnection = "server=.;database=GuidTest;Integrated Security=true;";
  12.        static void Main(string[] args)
  13.        {
  14.            Program app = new Program();
  15.            int Count = 10000;
  16.            Console.WriteLine("数据记录数为{0}",Count);
  17.            //自动id增长测试;
  18.            Stopwatch WatchId = new Stopwatch();
  19.            Console.WriteLine("自动增长id测试");
  20.            Console.WriteLine("开始测试");
  21.            WatchId.Start();
  22.            Console.WriteLine("测试中");
  23. 25            app.Id_InsertTest(Count);
  24.            //app.Id_ReadToTable(Count);
  25.            //app.Id_Count();
  26. 29            //查询第300000条记录;
  27.            //app.Id_SelectById();
  28. 32            WatchId.Stop();
  29.            Console.WriteLine("时间为{0}毫秒",WatchId.ElapsedMilliseconds);
  30.            Console.WriteLine("测试结束");
  31. 36            Console.WriteLine("-----------------------------------------");
  32.            //Guid测试;
  33.            Console.WriteLine("Guid测试");
  34.            Stopwatch WatchGuid = new Stopwatch();
  35.            Console.WriteLine("开始测试");
  36.            WatchGuid.Start();
  37.            Console.WriteLine("测试中");
  38. 44            app.Guid_InsertTest(Count);
  39.            //app.Guid_ReadToTable(Count);
  40.            //app.Guid_Count();
  41. 48            //查询第300000条记录;
  42.            //app.Guid_SelectById();
  43. 51            WatchGuid.Stop();
  44.            Console.WriteLine("时间为{0}毫秒", WatchGuid.ElapsedMilliseconds);
  45.            Console.WriteLine("测试结束");
  46.            Console.Read();
  47.        }
  48. 57        /**////
  49.        /// 自动增长id测试
  50.        ///
  51.        private void Id_InsertTest(int count)
  52.        {
  53.            string InsertSql="insert into Table_Id ([Value]) values ({0})";
  54.            using (SqlConnection conn = new SqlConnection(Connnection))
  55.            {
  56.                conn.Open();
  57.                SqlCommand com = new SqlCommand();
  58.                for (int i = 0; i < count; i++)
  59.                {
  60.                    com.Connection = conn;
  61.                    com.CommandText = string.Format(InsertSql, i);
  62.                    com.ExecuteNonQuery();
  63.                }
  64.            }
  65.        }
  66. 76        /**////
  67.        /// 将数据读到Table
  68.        ///
  69.        private void Id_ReadToTable(int count)
  70.        {
  71.            string ReadSql = "select top " + count.ToString() + " * from Table_Id";
  72.            using (SqlConnection conn = new SqlConnection(Connnection))
  73.            {
  74.                SqlCommand com = new SqlCommand(ReadSql, conn);
  75.                SqlDataAdapter adapter = new SqlDataAdapter(com);
  76.                DataSet ds = new DataSet();
  77.                adapter.Fill(ds);
  78.                Console.WriteLine("数据记录数为:{0}", ds.Tables[0].Rows.Count);
  79.            }
  80.        }
  81. 92        /**////
  82.        /// 数据记录行数测试
  83.        ///
  84.        private void Id_Count()
  85.        {
  86.            string ReadSql = "select Count(*) from Table_Id";
  87.            using (SqlConnection conn = new SqlConnection(Connnection))
  88.            {
  89.                SqlCommand com = new SqlCommand(ReadSql, conn);
  90.                conn.Open();
  91.                object CountResult = com.ExecuteScalar();
  92.                conn.Close();
  93.                Console.WriteLine("数据记录数为:{0}",CountResult);
  94.            }
  95.        }
  96. 108        /**////
  97.        /// 根据id查询;
  98.        ///
  99.        private void Id_SelectById()
  100.        {
  101.            string ReadSql = "select * from Table_Id where Id="+300000;
  102.            using (SqlConnection conn = new SqlConnection(Connnection))
  103.            {
  104.                SqlCommand com = new SqlCommand(ReadSql, conn);
  105.                conn.Open();
  106.                object IdResult = com.ExecuteScalar();
  107.                Console.WriteLine("Id为{0}", IdResult);
  108.                conn.Close();
  109.            }
  110.        }
  111.       
  112.        /**////
  113.        /// Guid测试;
  114.        ///
  115.        private void Guid_InsertTest(int count)
  116.        {
  117.            string InsertSql = "insert into Table_Guid ([Value]) values ({0})";
  118.            using (SqlConnection conn = new SqlConnection(Connnection))
  119.            {
  120.                conn.Open();
  121.                SqlCommand com = new SqlCommand();
  122.                for (int i = 0; i < count; i++)
  123.                {
  124.                    com.Connection = conn;
  125.                    com.CommandText = string.Format(InsertSql, i);
  126.                    com.ExecuteNonQuery();
  127.                }
  128.            }
  129.        }
  130. 143        /**////
  131.        /// Guid格式将数据库读到Table
  132.        ///
  133.        private void Guid_ReadToTable(int count)
  134.        {
  135.            string ReadSql = "select top "+count.ToString()+" * from Table_GuID";
  136.            using (SqlConnection conn = new SqlConnection(Connnection))
  137.            {
  138.                SqlCommand com = new SqlCommand(ReadSql, conn);
  139.                SqlDataAdapter adapter = new SqlDataAdapter(com);
  140.                DataSet ds = new DataSet();
  141.                adapter.Fill(ds);
  142.                Console.WriteLine("数据记录为:{0}", ds.Tables[0].Rows.Count);
  143.            }
  144.        }
  145. 159        /**////
  146.        /// 数据记录行数测试
  147.        ///
  148.        private void Guid_Count()
  149.        {
  150.            string ReadSql = "select Count(*) from Table_Guid";
  151.            using (SqlConnection conn = new SqlConnection(Connnection))
  152.            {
  153.                SqlCommand com = new SqlCommand(ReadSql, conn);
  154.                conn.Open();
  155.                object CountResult = com.ExecuteScalar();
  156.                conn.Close();
  157.                Console.WriteLine("数据记录为:{0}", CountResult);
  158.            }
  159.        }
  160. 175        /**////
  161.        /// 根据Guid查询;
  162.        ///
  163.        private void Guid_SelectById()
  164.        {
  165.            string ReadSql = "select * from Table_Guid where Guid='C1763624-036D-4DB9-A1E4-7E16318C30DE'";
  166.            using (SqlConnection conn = new SqlConnection(Connnection))
  167.            {
  168.                SqlCommand com = new SqlCommand(ReadSql, conn);
  169.                conn.Open();
  170.                object IdResult = com.ExecuteScalar();
  171.                Console.WriteLine("Guid为{0}", IdResult);
  172.                conn.Close();
  173.            }
  174.        }
  175.    }
  176. 192}
  177. 193
Kopírovat kód
3. Test vkládání do databáze
Test 1
Objem databáze je: 100 položek
Spusť výsledek
Test 2
Objem databáze je: 10 000 položek
Spusť výsledek

Test 3
Objem databáze je: 100 000 položek
Spusť výsledek
Test 4
Objem databáze je: 500 000 položek
Spusť výsledek
4. Přečíst data do DataSetu
Test 1
Množství přečtených dat: 100
Spusť výsledek
Test 2
Počet dat: 10 000
Spusť výsledek
Test 3
Množství dat: 100 000
Spusť výsledek
Test 4
Množství dat: 500 000
Spusť výsledek
4. Zaznamenat test celkového počtu
Výsledky testů
5. Specifikujte test dotazu na podmínku
300 000. záznam v databázi dotazů je 610 300.
4. Shrnutí:
Použití Guid jako hlavního klíče není příliš pomalé, ale je rychlejší než automatické růstové inkrementy.





Předchozí:asp.net převádět binární obsah Base64 na obrázky a ukládat je lokálně
Další:Řetězec[3]: vlastnost Velikost má neplatnou velikost 0.
Zřeknutí se:
Veškerý software, programovací materiály nebo články publikované organizací Code Farmer Network slouží pouze k učení a výzkumu; Výše uvedený obsah nesmí být používán pro komerční ani nelegální účely, jinak nesou všechny důsledky uživatelé. Informace na tomto webu pocházejí z internetu a spory o autorská práva s tímto webem nesouvisí. Musíte výše uvedený obsah ze svého počítače zcela smazat do 24 hodin od stažení. Pokud se vám program líbí, podporujte prosím originální software, kupte si registraci a získejte lepší skutečné služby. Pokud dojde k jakémukoli porušení, kontaktujte nás prosím e-mailem.

Mail To:help@itsvse.com