關於treeview的問題,請幫忙解決!(70分)

  • 主题发起人 主题发起人 empty023
  • 开始时间 开始时间
E

empty023

Unregistered / Unconfirmed
GUEST, unregistred user!
我在網上看見個關於treeview的程序,程序如下:
var
List: TStringList; //用于記錄各個id及其在樹中所對應的節點,從而實現快速查找

procedure MakeTree(Query: TADOQuery; TableName: string; TreeView: TTreeView);
begin
TreeView.Items.BeginUpdate;
list.Clear;
TreeView.items.clear;
if query.Active then query.Close;
Query.SQL.Text := 'SELECT * FROM ' + TableName + ' ORDER BY PID, ID';
Query.Open;
query.DisableControls;
TreeView.Items.Clear;
list.Clear;
List.Sorted := True;
query.First;
while not Query.Eof do
begin
addtreenode(Query, TreeView); //依次增加所有節點
Query.Next;
end;
TreeView.Items.EndUpdate;
query.EnableControls;
if treeview.Items.Count < 1 then exit;
treeview.Select(treeview.Items.Item[0]);
treeview.SetFocus;
end;

procedure addtreenode(Query: TADOQuery; TreeView: TTreeView; bj: boolean = false);
var
index: integer;
Node: TTreeNode;
begin
if Query.FieldByName('PID').AsInteger = 0 then { ParentID=0,頂層節點 }
Node := TreeView.Items.AddChildObject(nil, Query.FieldByName('CAPTION').AsString, query.GetBookmark)
//增加節點,並將本節點所對應的記錄標簽數據放到節點所提供的附加數據中
else
begin
Index := List.IndexOf(Query.FieldByName('PID').AsString);
Node := TreeView.Items.AddChildObjectFirst(TTreeNode(List.Objects[Index]),
Query.FieldByName('CAPTION').AsString, query.GetBookmark);
//增加子節點,并將本節點所對應的記錄標簽數據放到節點所提供的附加數據中

end;
//增加當前節點的信息到列表中,以實現在列表中快速查找節點的功能。
List.AddObject(Query.FieldByName('ID').AsString, Node);
if bj then
begin
treeview.Select(node);
treeview.SetFocus;
end;
end;
procedure AddChildNode(Query: TADOQuery; TreeView: TTreeView);
var
id: integer;
begin
id := query.FieldByName('ID').AsInteger; //記下當前的節點編號
query.Append;
query.FieldByName('PID').AsInteger := id; //新增加的子節點的父節點編號即為id
query.FieldByName('caption').AsString := '新子節點';
query.post;
addtreenode(query, treeview, true);
end;

procedure AddNode(Query: TADOQuery; TreeView: TTreeView);
var
pid: integer;
begin
pid := query.FieldByName('pID').AsInteger; //記下當前節點的父節點編號

query.Append;
query.FieldByName('PID').AsInteger := pid; //新增加的子節點的父節點編號即為pid

query.FieldByName('caption').AsString := '新節點';
query.post;
addtreenode(query, treeview, true);
end;

procedure Treechange(query: TADOQuery; node: TTreenode);
begin
query.GotoBookmark(node.Data);
end;

procedure TreeEdit(query: TADOQuery; text: string);
begin
query.Edit;
query.FieldByName('caption').AsString := text;
query.post;
end;

procedure treeselect(query: Tadoquery; TreeView: TTreeView);
var
index: integer;
Node: TTreeNode;
begin
Index := List.IndexOf(Query.FieldByName('ID').AsString);
Node := TTreeNode(List.Objects[Index]);
treeview.Selected := Node;
treeview.SetFocus;
end;

function TreeFind(TreeView: TTreeView; text: string): boolean;
var
i: integer;
begin
Result := false;
for i := 0 to treeview.Items.Count - 1 do
begin
if treeview.Items.Item.Text = text then
begin
treeview.Select(treeview.Items.Item);
treeview.SetFocus;
Result := true;
exit;
end;
end;
end;
initialization
List := TStringList.Create;
finalization
list.Free;
end.
程序能正常運行,但是它table裡的id與pid是integer型,我現在想把id與pid都換成string,請問要怎麼修改才能運行?
 
这句Query.FieldByName('ID').AsString已经转换了
 
首先我定義index: integer;Node: TTreeNode;然後用index of 方法找到字符串的位置Index := List.IndexOf(Query.FieldByName('PID').AsString);,接著把得到的字符串位置轉換位treenode,並增加節點,並將本節點所對應的記錄標簽數據放到節點所提供的附加數據中Node :=TreeView.Items.AddChildObjectFirst(TTreeNode(List.Objects[Index]),Query.FieldByName('CAPTION').AsString, query.GetBookmark);
如果數據庫表裡定義pid是integer 程序能正常運行,如果定義pid為varchar2類型,就會有list index out of bounds的錯誤,我想應該是在轉換treenode時的方法沒用對,但又不知道怎麼解決,請知道的幫忙解決。
 
这是典型的用ID、PID来表示的s树型结构。
PID表示其父亲的ID值,所以PID和ID的类型一定要一样。否则找不到。

另外,如果PID为字符串的话,那么可以认为FieldByName('PID').AsString=''表示根节点。且ID也要为字符串。

另外:GetBookmark必须执行其对应的FreeBookmark函数释放空间,否则有内存泄漏
 
就像xiammy所說的PID表示其父亲的ID值,我在數據庫表裡建立的id和pid是integer,程序運行無問題,但我現在想換數據表,用'網點名稱'與'所屬網點'來表示其父類關系,也就是說'所屬網點'是'網點名稱'的父類節點,它們在數據表中的類型是varchar2型,結果運行程序就會有list index out of bounds(-1)的錯誤.
另外:還有xiammy提到的GetBookmark必须执行其对应的FreeBookmark函数释放空间,否则有内存泄漏的問題,我想在問下,該在什麼地方什麼時候釋放?
 
今天進一步找到問題出錯在哪了,id,pid換成varchar2類型,程序也能正常運行,但只限與數字和英文字母,一輸入漢字我用的是繁體漢字,就會出錯。。 有誰知道怎麼解決?
 
后退
顶部