2011年10月10日 星期一

SQL SERVER-取得資料庫所有資料表,取得資料表所有欄

資料來源


SELECT * FROM INFORMATION_SCHEMA.Tables
SELECT * FROM INFORMATION_SCHEMA.Columns Where Table_Name = 'TableName'
SELECT 資料行名稱=COLUMN_Name ,資料型別=DATA_TYPE,長度=CHARACTER_MAXIMUM_LENGTH ,是否允許NULL=IS_NULLABLE , 預設值=COLUMN_DEFAULT FROM INFORMATION_SCHEMA.Columns Where Table_Name = 'TableName'

http://blog.miniasp.com/post/2007/11/How-to-get-detailed-Data-Dictionary-in-SQL-Server-2005.aspx

SELECT
a.TABLE_NAME as 表格名稱,
b.COLUMN_NAME as 欄位名稱,
b.DATA_TYPE as 資料型別,
b.CHARACTER_MAXIMUM_LENGTH as 最大長度,
b.COLUMN_DEFAULT as 預設值,
b.IS_NULLABLE as 允許空值,
(
SELECT
value
FROM
fn_listextendedproperty (NULL, 'schema', 'dbo', 'table', a.TABLE_NAME, 'column', default)
WHERE
name='MS_Description'
and objtype='COLUMN'
and objname Collate Chinese_Taiwan_Stroke_CI_AS = b.COLUMN_NAME
) as 欄位備註
FROM
INFORMATION_SCHEMA.TABLES a
LEFT JOIN INFORMATION_SCHEMA.COLUMNS b ON ( a.TABLE_NAME=b.TABLE_NAME )
WHERE
TABLE_TYPE='BASE TABLE'
ORDER BY
a.TABLE_NAME, ordinal_position

2011年10月6日 星期四

磁碟救援 TestDisk 使用教學


資料來源 

使用這軟體前,硬碟千萬不能用"格式化"!若磁碟已格式化,就無法用TestDisk找回檔案了。此外也不要再對硬碟執行其他動作,如磁碟分割、磁碟檢測、磁碟重組、磁碟掃描、SPFDISK.....等等,避免影響回覆資料的正確性。TestDisk是直接把分割表重新建立,所以檔案遺失後不要破壞掉分割檔,幾乎都可以完成救援。

軟體:TestDisk(軟體點此下載)
官網:http://www.cgsecurity.org/wiki/Main_Page
語言:英文
性質:免費軟體
適用系統:
DOS (either real or in a Windows 9x DOS-box),
Windows (NT4, 2000, XP, 2003),
Linux,
FreeBSD, NetBSD, OpenBSD,
SunOS and
MacOS

適用問題:誤刪了磁碟分區、因安裝作業系統、感染病毒而不慎毀損或遺失硬碟分區表...
這軟體比起其他的救援軟體有一個大優勢,就是只要硬碟資料能夠救援,大部分類型的檔案就可以救回了,其他軟體則是只能救回一些較普遍的文書資料檔或是影圖而已,所以這也是推薦TestDisk的原因之一。

使用方法:
下載完軟體後,執行在win資料夾內的 testdisk_win.exe
1.選擇[ No Log ]或[ Create ]後按enter

2.選取好要回復的硬碟,選擇[ Proceed ]後按enter
3.選擇[ Intel ]後按enter(windows系統適用)

4.選擇[Analyse]後按enter
5.選擇[ Quick Search ]後按enter
6.按 Y 後,按enter

7.選擇要救援的硬碟後按enter (不必輸入任何字母)
8.若沒有顯示搜尋到磁碟,則選擇[ Deeper Search ]再搜尋一次
有顯示的話,選擇[ Write ]後按enter

9.確認執行救援,按 Y 後,按enter
注意,在步驟9~10之間,若有出現 [Backup BS] 的選項,則須點選此選項才可救援。

10.畫面顯示 OK 按enter即可
11.選擇[ Quit ]離開

12.此時畫面會回到步驟2,若沒有要繼續救援其他磁碟,選擇[ Quit ]即可

13.重新開機後即可

2011年9月26日 星期一

悲觀鎖定

資料來源


在实际的多用户并发访问的生产环境里边,我们经常要尽可能的保持数据的一致性。而其中最典型的例子就是我们从表里边读取数据,检查验证后对数据进行修改,然后写回到数据库中。在读取和写入的过程中,如果在多用户并发的环境里边,其他用户已经把你要修改的数据进行了修改是非常有可能发生的情况,这样就造成了数据的不一致性。解决这样的办法,SQL Server提出了乐观定和悲观定的概念,下边我以一个实例来说明如何使用乐观定和悲观定来解决这样的问题。

/* 建立测试表:Card,代表一个真实的卡库,供用户注册.用户要从里边选出一个未使用的卡,也就是F_Flag=0的卡,给用户注册:更新 F_Name,F_Time,F_Flag字段. 如果出现两个用户同时更新一张卡的情况,是不能容忍的,也就是我们所说的数据不一致行。*/


create table Card(F_CardNO varchar(20),F_Name varchar(20),F_Flag bit,F_Time datetime)
Go
insert Card(F_CardNo,F_Flag) select '1111-1111',0
insert Card(F_CardNo,F_Flag) select '1111-1112',0
insert Card(F_CardNo,F_Flag) select '1111-1113',0
insert Card(F_CardNo,F_Flag) select '1111-1114',0
insert Card(F_CardNo,F_Flag) select '1111-1115',0
insert Card(F_CardNo,F_Flag) select '1111-1116',0
insert Card(F_CardNo,F_Flag) select '1111-1117',0
insert Card(F_CardNo,F_Flag) select '1111-1118',0
insert Card(F_CardNo,F_Flag) select '1111-1119',0
insert Card(F_CardNo,F_Flag) select '1111-1110',0
Go


-- 下边是我们经常使用的更新方案如下:

declare @CardNo varchar(20)
Begin Tran

       --  选择一张未使用的卡
        select top 1 @CardNo=F_CardNo
        from Card    where F_Flag=0
        
        --  延迟50秒,模拟并发访问.
        waitfor delay '000:00:50'

       --  把刚才选择出来的卡进行注册.

        update Card
        set F_Name=user,
            F_Time=getdate(),
            F_Flag=1
        where F_CardNo=@CardNo

commit


问题:如果我们在同一窗口执行同一段代码,但是去掉了waitfor delay子句.两边执行完毕后 我们发现尽管执行了两次注册,但是只注册了一张卡,也就是两个人注册了同一张卡.

悲观定解决方案

-- 我们只要对上边的代码做微小的改变就可以实现悲观的定.


declare @CardNo varchar(20)
Begin Tran

       --  选择一张未使用的卡
        select top 1 @CardNo=F_CardNo
        from Card   with (UPDLOCK)  where F_Flag=0
        
        --  延迟50秒,模拟并发访问.
        waitfor delay '000:00:50'

       --  把刚才选择出来的卡进行注册.

        update Card
        set F_Name=user,
            F_Time=getdate(),
            F_Flag=1
        where F_CardNo=@CardNo

commit

鎖定簡介

資料來源



ROWLOCK 讀取或修改資料時使用資料列層級鎖定。這些鎖定會依適當情況被取得及釋放。

PAGLOCK 讀取或修改資料時使用頁面層級鎖定。這些鎖定會依適當情況被取得及釋放。

TABLOCK 讀取或修改資料時使用資料表鎖定。此鎖定會被保留到陳述式結束為止。

DBLOCK 讀取或修改資料時使用資料庫鎖定。此鎖定會被保留到陳述式結束為止。

LOCKMODES

UPDLOCK 在讀取資料表時使用更新鎖定,而非共用鎖定,並使用保留鎖定直到陳述式或交易結束為止。UPDLOCK 可讓您不會在讀取資料時封鎖其他讀取器,且稍後更新資料時,也可確信自從您上次讀取之後,資料並未發生變更。

XLOCK 在讀取資料表時使用獨佔鎖定,而非共用鎖定,並使用保留鎖定直到陳述式或交易結束為止。

持續期間

HOLDLOCK 使用保留鎖定將鎖定保留至交易完成為止,而不會在所需資料表、資料列或資料頁已不再需要時立即釋放鎖定。

NOLOCK 不會發出任何鎖定。這是 SELECT 作業的預設值。此鎖定不適用於 INSERT、UPDATE 及 DELETE 陳述式。

範例:

begin tran begin tran select * from test1 with (xlock) where t1 = 1 '鎖定t1=1的資料

rollback

begin tran begin tran select * from test1 with (tablock,xlock) '鎖定資料表Test1

rollback

鎖定

在 說明SQL Server的鎖定原理之前,首先來看一個基本的問題,為什麼要使用鎖定?我們可以從逆向思考的方式來回答這個問題,也就是不使用鎖定,會出現什麼問題, 特別是當多人同時存取資料時,若不使用鎖定,可能會發生lost update、dirty read、nonrepeatable read與phantoms read等問題。這也是為什麼要使用鎖定的主要原因。
談 到鎖定,就不得不談到交易處理(transaction)。所謂交易處理是指在一個工作單元中,執行的一系列資料操作。ATM跨行轉帳就是一個很典型的例 子,這個工作單元中包含從轉出帳戶扣款與將金額存入轉入帳號兩個操作,這兩個操作必須有一致的結果,不是全部成功,確認最終狀態;就是全部失敗,回復原始 狀態,沒有部分成功,部分失敗的情況,只有轉出沒有轉入或只有轉入沒有轉出都是不允許的。也就是交易處理具有不可分割性(Atomicity)、一致性 (Consistency)、隔離性(Isolation)以及持久性(Durability)等特性。而鎖定機制便是為了實現交易的隔離性,好像此時資 料庫系統是專屬你一個人的。
鎖定的範圍
在SQL Server可以鎖定哪些資源?依據鎖定的範圍可以分成RID 列級鎖定、Key 索引鎖定、Page 頁級鎖定、Extent 擴展鎖定(每8個Page為1個extent,用於SQL Server儲存空間的分配)、Table 表級鎖定,以及Database 資料庫級鎖定。
鎖 定的範圍越小,耗用的資源越大;鎖定的範圍越大,耗用的資源越小。列級鎖定可以增加同時線上(concurrent)數量,但卻增加資源花費;頁級或表級 鎖定則正好相反。SQL Server會衡量目前的concurrent數量與系統資源,自動管理鎖定的範圍,同時為了獲得最佳的鎖定效能,SQL Server提供一種動態鎖定的機制,也就適當列級鎖定耗用的資源達到某個程度時,SQL Server會自動將列級鎖定升級成頁級或表級鎖定。
鎖定的類型
SQL Server鎖定可以分成基本鎖定與特殊鎖定兩大類。基本鎖定又可分成共用鎖定(shared lock)與獨占鎖定(exclusive lock) 。一般而言,當Select資料時會使用共用鎖定,Insert、Update和Delete資料時會使用獨佔鎖定。特殊鎖定又可分成意圖鎖定 (Intent lock)、更新鎖定(Update lock)、綱要鎖定(Schema lock)與大量新鎖定(Bulk update lock)。接下來,對常用的鎖定類型,簡單說明如下:
共用鎖定
當讀取資料時,SQL Server會使用共用鎖定,即使尚未結束,其他交易也可以獲得共用鎖定,也就是說多個交易可以同時讀取table、page、key和row。
獨佔鎖定
當修改資料時,SQL Server會使用獨佔鎖定。在交易結束之前,其他交易的鎖定請求都會被拒絕。一個資源只能有一個獨佔鎖定,當一個交易對某個資源進行獨占鎖定時,其他交易無法讀取該資源,由此可知,這種鎖定會限制了同時線上數量。
更新鎖定是共用鎖定與獨占鎖定的混合體。在修改之前會使用共用鎖定,其他交易可以讀取被鎖定的資料,但不可以修改。一旦開始修改時,就變成了獨占鎖定,其他交易無法讀取和更新被鎖定的資料,直到交易結束。
一個鎖定可以與另一個鎖定同時使用,這種特性稱為鎖定的相容性。相反的,若一個交易正在操作而鎖定資料,另一個交易必須等前一個交易結束後,才能繼續,則稱為不相容。相容性越好,表示支援的同時線上數量越大。哪些鎖定式相容的?哪些鎖定又是不相容的?一般的原則如下:
共用鎖定可以與獨占鎖定之外的其他鎖定相容。多個交易可以在相同資料上獲得共用鎖定,但沒有一個交易可以在已經獲得共用鎖定的資料上獲得獨佔鎖定。
獨占鎖定不可以其他鎖定相容。
更新鎖定只能與共用鎖定相容。
我們可以使用交易的隔離級別來設定鎖定的策略,以防止前面提到多人存取所可能出現的問題。SQL Server提供下列4種交易隔離級別,其特性簡單說明如下。
read uncommitted 會出現dirty read、non-repeatable read與phantoms等問題。
read committed 會出現non-repeatable read與phantoms等問題。
repeatable read 會出現phantoms的問題。
serializable 無
若 未指定SQL Server預設使用read committed。在SQL Server 2005,提供了另外兩個基於資料版本的隔離級別,snapshot與Read Committed using Statement-level Snapshot(RCSI),使得讀取與更新的操作不會互相影響,加快交易的執行速度。
除 了隔離級別的鎖定策略之外,您也可以使用鎖定提示來控制資料表的鎖定行為,以及覆蓋目前交易的隔離級別的鎖定策略。當隔離級別的鎖定策略與鎖定提示相衝突 時, SQL Server是採用級別越小越優先的處理原則。例如,使用serializable隔離級別,若在交易中使用with (nolock)讀取資料,SQL Server會允許其他交易讀取資料。可用的表級鎖定提示摘要如下:
holdlock:當交易開始之後,交易結束之前,不允許其他交易讀取被holdlock的資料。
nolock:不使用任何的鎖定。
使用rowlock、paglock,tablock與tablockx來指定資料表的鎖定類型和大小。例如使用tablockx表示當讀取資料列時,在資料列所在的資料表上使用獨占索定。
readpast:忽略鎖定的資料列
updlock:當讀取資料使用更新鎖定,而不是預設的共用鎖定。當交易尚未結束前,不允許其他交易更新被updlock的資料,可避免non-repeatable read。
您可以根據個別的需要來組合這些鎖定提示,以獲得更加靈活、更有彈性的應用。例如,with (paglock, holdlock)表示在資料列所在的資料頁上使用hold lock。

2011年7月9日 星期六

如何判斷正在執行的是哪一版本的 SQL Server

SQL SERVER 2000 - 2008 使用
SELECT SERVERPROPERTY('productversion'),SERVERPROPERTY ('productlevel'),SERVERPROPERTY ('edition')

SQL SERVER 6.5 - 7.0 使用
SELECT @@VERSION

2011年7月8日 星期五

SQL Server 偵測到邏輯的一致性 I/O 錯誤

訊息 8921,層級 16,狀態 1,行 1
檢查結束。收集事實時偵測到失敗。可能是由於 tempdb 空間用完或系統資料表不一致。請檢查先前的錯誤。
訊息 824,層級 24,狀態 2,行 1
SQL Server 偵測到邏輯的一致性 I/O 錯誤: 不正確的頁面識別碼 (預期是 1:98000; 實際是 0:0)。這是當在檔案 'D:\MSSQL\CSERPSOFT.mdf' 中位移 0x0000002fda0000 的資料庫識別碼 5 之頁面 (1:98000) 進行 讀取 的期間所發生的。SQL Server 錯誤記錄檔和系統事件記錄檔中的訊息,或許可以提供其他詳細資訊。這是嚴重的錯誤狀況,且可能會損及資料庫的完整性,所以必須立即更正。請執行完整的資料庫一致性檢查 (DBCC CHECKDB)。會導致這個錯誤的原因有許多可能性; 如需詳細資訊,請參閱《SQL Server 線上叢書》。

此問題通常都是硬碟異常引起

1. 請先備份資料庫檔案
2. 利用Microsoft SQL Server Management Studio建立一新資料庫
    將損毀的資料庫中的資料表紀錄
    利用Insert * into NewDataBase.dbo.TableName FROM TableName 轉出
3. 使用下列方式處理
    1. 設定有疑問的資料庫為緊急模式
      ALTER DATABASE cserpsoft SET EMERGENCY
    2. 檢查資料庫狀態
      DBCC checkdb('cserpsoft')
    3. 設定資料庫為SINGLE_USER 和 修復模式
       ALTER DATABASE cserpsoft SET SINGLE_USER WITH ROLLBACK IMMEDIATE
    4. 進行修復
      DBCC CheckDB ('cserpsoft', REPAIR_ALLOW_DATA_LOSS)
    5. 還原資料庫為多人使用模式
       ALTER DATABASE cserpsoft SET MULTI_USER
4. 檢查硬碟並且修復 

2011年3月23日 星期三

SQL SERVER 2005 資料庫突然出現(有疑問)

使用下列方式處理

1. 設定有疑問的資料庫為緊急模式
ALTER DATABASE cserpsoft
            SET EMERGENCY

2. 檢查資料庫狀態
DBCC checkdb('cserpsoft')

3. 設定資料庫為SINGLE_USER 和 修復模式
ALTER DATABASE cserpsoft
           SET SINGLE_USER
           WITH ROLLBACK IMMEDIATE

4. 進行修復
DBCC CheckDB ('cserpsoft', REPAIR_ALLOW_DATA_LOSS)

5. 還原資料庫為多人使用模式
ALTER DATABASE cserpsoft
            SET MULTI_USER

使用指令關閉或開啟具名的 Microsoft SQL Server 執行個體服務

以下面的指令而言,分別是關閉然後再啟動執行個體名稱為 SQLExpress 的服務:
1.net stop "SQL Server (SQLEXPRESS)"
2.net start "SQL Server (SQLEXPRESS)"
位於 stop 與 start 之後的指令,因為內有空白,所以必須使用一對引號將其包含起來。


如果是要關閉並啟動預設的 SQL Server 執行個體,要改用如下的指令:

1.net stop MSSQLServer
2.net start MSSQLServer

 一般而言,我們都會讓 MS SQL Server 以服務的方式啟動,因此可以透過控制台裡的「排定的工作」來定時將 MS SQL Server 的服務關閉與啟動,作業系統(Windows NT/2000/XP/2003)內建一個「net」指令,裡面提供了的兩個子指令:「net stop」與「net start」可以讓管理者透過指令模式即可關閉與啟動某項服務,因此將下面的指令加入「排定的工作」之後,就可以讓 MS SQL 在固定的時間自動關閉跟開啟。

關閉 MS SQL:  
net stop MSSQLServer /y
(記得要加上 /y 的參數,要不然是不會自動關閉的)  

啟動 MS SQL:  
net start MSSQLServer

若您有需要啟動 SQL Server Agent 的話,在啟動時,需要在啟動 SQL Server 服務之後,順便啟動 SQL Server Agent,因為當您關閉 SQL Server 時,會一起關閉 SQL Server Agent,指令如下: 
net start SQLServerAgent

啟動亦可用直接使用 SQLServr 這個指令,但是使用這個指令啟動的話,MS SQL Server 就不是以服務的方式執行了。使用這個方式啟動的好處是,您可以即時監看 SQL 目前的狀況,其實這個就是在 SQL Server Enterprise Manager 裡面的 Management -> SQL Server Logs 裡所看到的 log。

2011年3月9日 星期三

TextBox 控制項

移動游標到TextBox控制項內容開頭
tbTextBox.Select( 0, 0 )

移動游標到TextBox控制項內容結尾
tbTextBox.Select( tbTextBox.Text.Length, 0 )

在 TextBox 控制項中設定焦點
tbTextBox.Focus()

偵測 TextBox 中的文字何時變更
使用TextChanged事件

設定TextBox輸入文字的長度
使用MaxLength屬設定   例如 : tbTextBox.MaxLength = 10

設定TextBox內文字顯示的位置
使用TextAlign屬性設定  例如 : tbTextBox.TextAlign =
HorizontalAlignment.Left        靠左對齊
HorizontalAlignment.Center    置中
HorizontalAlignment.Right      靠右對齊