線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:1442
推到 Plurk!
推到 Facebook!

紀錄新增數據動作的問題

答題得分者是:cashxin2002
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#1 引用回覆 回覆 發表時間:2005-01-13 01:15:01 IP:222.79.xxx.xxx 未訂閱
access數據庫在插入的時候自動計數字段總是沒有顯示出數字,要等插入完保存了之後才顯示,請問我應該在哪個事件裏添加代碼,才能在添加紀錄完之後立即把該紀錄的自動計數等其他若干字段插入到另一個表中?比如我現在錄入一個新員工的數据后,另一個表能插入一行紀錄下這個新員工的ID(自動編號),姓名,當前時間,並寫下"新增員工",我做的老是讀取不了那個未生成的自動編號,請告訴我一下思路,謝謝
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#2 引用回覆 回覆 發表時間:2005-01-13 09:18:14 IP:202.62.xxx.xxx 未訂閱
您好﹗    照您的描述﹐這兩個資料表是互相關聯的﹐也就是說兩個資料表中自動編號欄位值應是相同的﹐因為每新增一筆資料時﹐都要在另一個資料表中新增一筆資料﹐每刪除一筆資料的時候﹐也會在另一個表中刪除相對應的資料﹐那樣的話﹐就不需要記錄自動編號欄位的值了﹐只需要在第一個資料表對應的資料集元件的BeforePost事件中使用變數記錄下此筆資料的姓名欄位值﹐然后在AfterPost事件中﹐再在對應第二個資料表的資料集元件中新增一筆資料﹐賦予其姓名值等于之前記錄下的變數等值﹒    ================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================
------
忻晟
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#3 引用回覆 回覆 發表時間:2005-01-13 10:36:24 IP:222.79.xxx.xxx 未訂閱
cashxin2002不好意思,可能是我描述的不清楚。我現在要實現的是員工變動紀錄表,在員工表新增或刪除員工后,都會插入一條類似“新增員工”或“員工離職”的紀錄到員工變動紀錄表當中。可是就是不懂得如何記下當前要更改的員工的自動編號ID。
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#4 引用回覆 回覆 發表時間:2005-01-13 14:29:04 IP:202.62.xxx.xxx 未訂閱
您好﹗
可先在Private區域宣告孌數﹕
private
    { Private declarations }
  I : Integer;    然后在資料集元件的BeforePost和BeforeDelete中記錄﹕
begin
  I := ADOTable1.Fields.Fields[0].Value;
end;
================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================ 發表人 - cashxin2002 於 2005/01/13 14:34:43
------
忻晟
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#5 引用回覆 回覆 發表時間:2005-01-14 15:50:41 IP:222.77.xxx.xxx 未訂閱
謝謝cashxin2002,我試過了您的方法但是還是不能用ADOTable1.Fields.Fields[0].Value是variant類型的,於是我把I也聲明成variant在轉成string,但是讀出來的是空值。
Fishman
尊榮會員


發表:120
回覆:1949
積分:2163
註冊:2006-10-28

發送簡訊給我
#6 引用回覆 回覆 發表時間:2005-01-14 16:18:23 IP:210.65.xxx.xxx 未訂閱
Hi oktony,    在 Post 該筆記錄後取值,以下假設欄位 ID 為自動編號,在 Append 時,不要對 ID 給值,直接 Post 後在取值
procedure TForm1.Button1Click(Sender: TObject);
VAR
  I : integer;
begin
  ADOTable1.Append;
  ADOTable1.FieldByName('Name').AsString := 'Name';
  ADOTable1.FieldByName('DESCRIPTION').AsString := 'Description';
  ...
  ADOTable1.Post;
  I := ADOTable1.FieldByName('ID').AsVariant;
  ShowMessage(IntToStr(I));
end;
---------------------------------- 小弟才疏學淺,若有謬誤尚請不吝指教 ----------------------------------
------
Fishman
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#7 引用回覆 回覆 發表時間:2005-01-14 18:33:37 IP:202.62.xxx.xxx 未訂閱
引言: 謝謝cashxin2002,我試過了您的方法但是還是不能用ADOTable1.Fields.Fields[0].Value是variant類型的,於是我把I也聲明成variant在轉成string,但是讀出來的是空值。
您好﹗ 此方法小弟有試過﹐應該可行﹒ 在抓取ADOTable1.Fields.Fields[0].Value的值時﹐雖然抓出的是自動編號形態的值﹐但在賦值給I(Integer)變數時﹐其還是會正确以Integer形態取得此值﹐能否貼出相關程式碼部分﹐看看是不是其它地方的錯誤﹒ ================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================
------
忻晟
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#8 引用回覆 回覆 發表時間:2005-01-14 22:13:24 IP:222.79.xxx.xxx 未訂閱
謝謝fishman,不過我用你的方法post之後會跑到第一條記錄不知道爲什麽。cashxin2002兄我再試了一次還是不行,還有説明一下我添加是在dbedit裏面添加紀錄的,應該沒有影響吧? 貼出code如下:
procedure TEmployee.tUserBeforePost(DataSet: TDataSet);
begin
  inherited;         //基類沒有添加BeforePost事件      
 i:=tUser.Fields.Fields[0].Value;  //運行到這行出錯提示空的var類型不能賦給int類型,調試可以發現Value為空值
    with ADOQuery1 do
    begin
      Close;
      SQL.Clear;
      SQL.Add('INSERT INTO personnel_change([empID],[name],[changetime],[memo]) VALUES');
      SQL.Add('(:empID,:name,:changetime,:memo)');
      Parameters.ParamValues['empID'] := i;
      Parameters.ParamValues['name'] := dbeName.Text;
      Parameters.ParamValues['changetime'] := DateToStr(Date);
      Parameters.ParamValues['memo'] := '加入新员工';
      ExecSQL;
      MessageBox(0, '添加成功!', '提示', MB_OK   MB_ICONINFORMATION);
    end;  }
end;
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#9 引用回覆 回覆 發表時間:2005-01-15 18:15:55 IP:202.62.xxx.xxx 未訂閱
您好﹗    Fields[0]不是自動編號欄位嗎﹖怎么會取出空值的﹖ 使用Integer形態變數﹐不要用Variant形態變數﹒ 您在personnel_change資料表中EmpID欄位也需設為Integer形態﹒
private
  { Private declarations }
  I : Integer;    procedure TEmployee.tUserBeforePost(DataSet: TDataSet);
begin
 inherited;         //基類沒有添加BeforePost事件      
 I:=tUser.Fields.Fields[0].Value
end;    procedure TEmployee.tUserAfterPost(DataSet: TDataSet);
begin
  with ADOQuery1 do
    begin
      Close;
      SQL.Clear;
      SQL.Add('INSERT INTO personnel_change([empID],[name],[changetime],[memo]) VALUES');
      SQL.Add('(:empID,:name,:changetime,:memo)');
      Parameters.ParamValues['empID'] := I;
      Parameters.ParamValues['name'] := dbeName.Text;
      Parameters.ParamValues['changetime'] := DateToStr(Date);
      Parameters.ParamValues['memo'] := '加入新员工';
      ExecSQL;
      MessageBox(0, '添加成功!', '提示', MB_OK + MB_ICONINFORMATION);
    end;
end;
================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================
------
忻晟
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#10 引用回覆 回覆 發表時間:2005-01-16 13:32:23 IP:222.79.xxx.xxx 未訂閱
不好意思,小弟試過了還是不行。因爲這個form有個DBGrid,因此我在插入新的紀錄的時候可以看到DBGrid生成一行空行,然後在DBEdit裏面填的數據會在DBGrid實時顯示出來,可以明顯的看到自動編號這個字段是空白的,等post完之後它才自動填上編號的。我用單步調試也可以看到在beforepost的時候自動編號是空白的。
huangchin
一般會員


發表:3
回覆:18
積分:4
註冊:2002-12-24

發送簡訊給我
#11 引用回覆 回覆 發表時間:2005-01-16 22:27:19 IP:203.204.xxx.xxx 未訂閱
經過測試後,大家的狀況應該都"沒錯"唷....    我覺得問題是在於使用SQL指令做Insert動作以及以TADOQuery.Insert 的方式做Insert動作,如果是使用SQL指令的方式,afterPost這個Event不 會啟動,而且傳回的DataSet是SQL指令所影響的資料列數, 這樣是一定抓不到自動增加後的值.    若是使用元件提供的Insert動作時,經過元件的運作, afterPost這個Event可以動作,而且也可以抓到自動增加後的值.    不確定我這樣的論點是否正確,如果有錯誤,還麻煩不吝指正唷...^^    
procedure TForm1.Button1Click(Sender: TObject);
begin
  ADOConnection1.Open;
  ADOQuery1.Close;
  ADOQuery1.SQL.Text := 'SELECT * FROM table1';
  ADOQuery1.Open;      ADOQuery1.Insert;
  ADOQuery1['user_name'] := 'ccc';
  ADOQuery1.Post;
end;    procedure TForm1.ADOQuery1AfterPost(DataSet: TDataSet);
begin
  ShowMessage(VarToStr(ADOQuery1['user_id']));
end;
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#12 引用回覆 回覆 發表時間:2005-01-16 23:10:18 IP:222.77.xxx.xxx 未訂閱
謝謝huangchin兄,您的方法跟Fishman兄是一樣的,我用的是ADOQuery1.Insert方式,post之後還沒來的及afterpost事件發生,紀錄馬上就會跑到第一條了。我用的是adodataset,我現在想求證的是,adodataset在post之後是不是紀錄馬上會跑到第一條?如果是的話,證明我有其他的動作會影響到post之後紀錄的移動。可是我明明把別的有關代碼全都屏蔽掉了執行還是會跑到第一條阿。
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#13 引用回覆 回覆 發表時間:2005-01-17 09:00:58 IP:202.62.xxx.xxx 未訂閱
您好﹗    Access資料庫在新增資料后﹐如果沒有Close&Open的動作﹐資料錄指針是停留在新增筆的資料錄上﹒    ================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================
------
忻晟
huangchin
一般會員


發表:3
回覆:18
積分:4
註冊:2002-12-24

發送簡訊給我
#14 引用回覆 回覆 發表時間:2005-01-17 11:26:34 IP:203.204.xxx.xxx 未訂閱
如果前面幾位先進所說,Isert後若沒有Open or Close動作,指料指標應該是 停留在新增的那筆上,早上還重新了支小程式測試過,我想可能是否是在 您的專案中有其它的動作或是Event所影響. 另外,新增資料時,自動編號是在寫入資料庫時才會產生的資料, 所以在beforePost這個Event中是抓不到新資料, 並需在afterPost這個Event中才抓的到. 至於delete要在beforeDelete這個Event,至於edit動作的話, 就要看您的記錄需求嘍...^^ 建議您先寫個獨立的小程式測試一下幾位先進提供的意見, 確認後再檢視您的專案,說不定會有"新"發現唷...^^
cashxin2002
版主


發表:231
回覆:2555
積分:1937
註冊:2003-03-28

發送簡訊給我
#15 引用回覆 回覆 發表時間:2005-01-17 11:51:29 IP:202.62.xxx.xxx 未訂閱
您好﹗    小弟也做了個小測試﹒ 無論資料集元件是Insert還是Edit﹐當Post之后﹐尚未做Close&Open的動作﹐當然也包括Locate等方法引起的資料錄指針移動時﹐資料錄指針依然停留在Insert的資料錄或是被Edit的資料錄上﹒    資料集元件在BeforePost事件中抓不到自動編號欄位值﹐所以同huangchin兄所述﹐可以把抓取自動編號欄位值的程式碼和將資料新增到另一個資料庫的程式碼都寫在AfterPost事件中﹐記得使用另外的資料集元件來做﹐因為如果使用同一個資料集元件﹐即會触發資料錄指針的移動了﹒    另外﹐自動編號欄位值可賦值給Integer變數﹐相關程式碼如下﹕
private
  { Private declarations }
  I : Integer;    procedure TEmployee.tUserAfterPost(DataSet: TDataSet);
begin
  I := tUser.Fields.Fields[0].AsInteger;  
  with ADOQuery1 do
    begin
      Close;
      SQL.Clear;
      SQL.Add('INSERT INTO personnel_change([empID],[name],[changetime],[memo]) VALUES');
      SQL.Add('(:empID,:name,:changetime,:memo)');
      Parameters.ParamValues['empID'] := I;
      Parameters.ParamValues['name'] := dbeName.Text;
      Parameters.ParamValues['changetime'] := DateToStr(Date);
      Parameters.ParamValues['memo'] := '加入新员工';
      ExecSQL;
      MessageBox(0, '添加成功!', '提示', MB_OK + MB_ICONINFORMATION);
    end;
end;
供參考﹗ ================================= 有空來瞅瞅我﹗因為我是您的朋友﹐有您真好﹗ ================================
------
忻晟
oktony
中階會員


發表:67
回覆:132
積分:64
註冊:2004-12-05

發送簡訊給我
#16 引用回覆 回覆 發表時間:2005-01-17 12:47:34 IP:222.79.xxx.xxx 未訂閱
實在是太感謝各位大大的幫助了,特別是cashxin2002兄,確實是有別的event在af terpost之前發生導致紀錄移到第一筆,由於小弟的疏忽給各位造成麻煩真不好意思。
系統時間:2024-06-29 23:17:19
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!