关于数据库与算法问题。头大!   我第一天上班,就遇到这个难题.拜托高手写给我代码看看阿!  在下万分感激.1。有一个表有2个子段。如下:
    历史       现状
    A1          A5
    A2          A5
    A3          A5
    A4          A6
    A4          A7
    A5          A8
    A6          A8
    A7          A8
2.我现在第一次搜索到了A8,然后用一个Treevie1控件显示。显示为根节点“数据表”之下。例如如下树的显示:
--A8
------A7
------A7
------A5
   
3.然后又搜索A7对应的 "现状" 的内容对应为:
--A8
------A7
----------A4
------A7
------A54.我的意思就是这样的 先找"现状"表中的A8,.现状中的A8所对应的有3个历史记录,就把这3个对应的"历史"作为A8的子节点列出来.然后再分别搜寻A5,A6,A7所对应的"现状"中有没有他们,如果有,就找"历史"(如上图A7又对应了A4 ).5.如果有这样很多循环的循环.要求如上图结构列出到Treeview中.如何做???6.我第一天上班,就遇到这个难题.拜托高手写给我代码看看阿!

解决方案 »

  1.   

    Private Sub Command4_Click()
    Dim sityCode As String
    Dim PATHstr As String
    Dim SQLstr As String
    Dim SQLstr1 As String
        GS_Haein_DataBase = "C:\HALIS\Database" '调试后删除
        SSQCode = "210202" ' 调试后删除
        sityCode = Left(SSQCode, 4)
        quCode = Right(SSQCode, 2)
        PATHstr = GS_Haein_DataBase & "\" & sityCode & "\" & quCode & "Lib.mdb"
        
        If Not MDB_Connect(PATHstr) Then Exit Sub    Set MDB_RS_HIS = New ADODB.Recordset
        Set MDB_RS_HIS1 = New ADODB.RecordsetTreeView1.Nodes.Clear
    Dim Nodx As Node, XianZ As String, XianS As String, LishiZ As String, LishiS As String
    TreeView1.ImageList = ImageList1Call ZDBEnd Sub
    Public Sub ZDB()    SQLstr = "select * from Xzzdb where XZZDH='" & Text1.Text & "'"  '这是现状宗地表的内容(包括 申请书号)
        MDB_RS_HIS.Open SQLstr, MDB_DB, adOpenKeyset, adLockOptimistic
        MDB_RS_HIS.MoveLast
       For i = 0 To MDB_RS_HIS.RecordCount - 1
          If Text1.Text = MDB_RS_HIS!XZZDH Then
             XianZ = MDB_RS_HIS!XZZDH
          Else
             MDB_RS_HIS.MovePrevious
          End If
       Next   If XianZ <> "" Then
          XianS = MDB_RS_HIS!XZZDSQSH
          Set Nodx = TreeView1.Nodes.Add(, , , "现状宗地号为【" & XianZ & "】   申请书号为【" & XianS & "】", "pic1")
       Else
          MsgBox "您没有输入要追溯的现状宗地号,或者您输入的现状宗地号不存在", 64, "提示"
          Text1.SetFocus
          Text1.Text = ""
       End If
    MDB_RS_HIS.Close'----------------------------------------------------------------------------------------------   SQLstr = "select * from XzyLszdb"          '取得现状历史宗地表的历史申请书号
       MDB_RS_HIS.Open SQLstr, MDB_DB, adOpenKeyset, adLockOptimistic
       Set Nodx = TreeView1.Nodes.Add(, , , "历史资料" & LishiS, "pic1")
       
       MDB_RS_HIS.MoveLast
       For i = 0 To MDB_RS_HIS.RecordCount - 1
          If XianS = MDB_RS_HIS!XZZDSQSH Then
              LishiS = MDB_RS_HIS!LSZDSQSH
              
    '           '------------
    '             SQLstr = "select * from lszdb"       '取得现状历史宗地表的历史宗地号
    '             MDB_RS_HIS1.Open SQLstr, MDB_DB, adOpenKeyset, adLockOptimistic
    '             MDB_RS_HIS1.MoveLast
    '                For q = 0 To MDB_RS_HIS1.RecordCount - 1
    '                If LishiS = MDB_RS_HIS1!LSZDSQSH Then
    '                   LishiZ = MDB_RS_HIS1!LSZDH
    '                End If
    '                MDB_RS_HIS1.MovePrevious
    '                Next
    '             MDB_RS_HIS1.Close
    '           '------------          '根据历史申请书号找现状申请书号
    '                   SQLstr = "select * from XzyLszdb"          '取得现状历史宗地表的历史申请书号
    '                   MDB_RS_HIS.Open SQLstr, MDB_DB, adOpenKeyset, adLockOptimistic
    '                   MDB_RS_HIS.MoveLast
    '                   For q1 = 0 To MDB_RS_HIS.RecordCount - 1
    '                      If LishiS1 = MDB_RS_HIS!LSZDSQSH Then
    '                         XianS1 = MDB_RS_HIS!XZZDSQSH
    '                      End If
    '                   MDB_RS_HIS.MovePrevious
    '                   Next
                       
              
              Set Nodx = TreeView1.Nodes.Add(2, tvwChild, , "历史宗地号为【" & LishiZ & "】   历史申请书号为【" & LishiS & "】", "pic2")
                        
              MDB_RS_HIS.MovePrevious      End If
       Next'Nodx.EnsureVisible           '启动即显示全部节点End Sub
      

  2.   

    楼主的意思很清楚,要把那个表写进treeview ,两个字段之间的关联关系也说得很明白,现状对着历史,其中有一嵌套问题,可能会有N个循环,问可不可以有更好的办法!
      

  3.   

    感谢cdknet(cdksoft) !!  就是我太笨,写不出来。55555555555
      

  4.   

    TreeView1.Nodes.Add('', tvwChild, "A8","A8", "pic1")
    Make_Tree("A8")Private Sub Make_Tree(上级代码 As String)
    SQLstr="Select distinct 历史 from 表 where 现状=上级代码  order by 历史"
    MDB_RS_HIS.Open SQLstr, MDB_DB, adOpenKeyset, adLockOptimisticDo While Not MDB_RS_HIS.EOF
        
        Set N = TreeView1.Nodes.Add(上级代码, tvwChild, MDB_RS_HIS!历史, MDB_RS_HIS!历史, "pic1")
        N.Expanded = False
        Make_Tree(MDB_RS_HIS!历史)
        MDB_RS_HIS.MoveNext
    Loop
    '下面这句不知道要不要,你试试
    MDB_RS_HIS.Close()
    End Sub'我不会VB,以上仅供参考
      

  5.   

    只有那一个表两个字段吗?那可是很容易被死循环的呢
    历史    现状
    A1      A2
    A2      A1
    ………如果表里有这种关系是不是无限找下去?还是简单的A2下放个A1,A1下放个A2,像这样放:
    A2
     ...A1
        ...A2
      

  6.   

    cdknet(cdksoft) ,只有那一个表两个字段.如果表里有这种关系是需要无限找.不是简单的A2下放个A1,A1下放个A2,数据是动态的.
      

  7.   

    wd_318(初学者.net),王兄!!感谢!!
      

  8.   

    不会吧,难道是:
    A2
     ...A1
         ...A2
            ...A1
              ...A2
                 ...A1
                    ...A2
                       ...A1
                           
    这样就是死循环呢,你不认为吗?现状A2的历史是A1,现状A1的历史是A2,这个A1,A2就无限的关联了嘛,这样没有道理啊?
      

  9.   

    兄弟,你看这个结构:
    3.然后又搜索A7对应的 "现状" 的内容对应为:
    --A8
    ------A7
    ----------A4
    ------A7
    ------A5到了A4.就结束了.
      

  10.   

    你看一下这个表里的关系:
    1。有一个表有2个子段。如下:
        历史       现状
        A1          A5
        A2          A5
        A3          A5
        A4          A6
        A4          A7
        A5          A8
        A6          A8
        A7          A8到A4就结束了
      

  11.   

    你看一下这个表里的关系:
    1。有一个表有2个子段。如下:
        历史       现状
        A1          A5
        A2          A5
        A3          A5
        A4          A6
        A4          A7
        A5          A8
        A6          A8
        A7          A8到A4就结束了
      

  12.   

    无限找下去我知道,
      A2
       ...A4
         ....A8
           ....A12
               ....An我就是想知道如果相互关联了怎么办?
      

  13.   

    最终结果是这样的:--A8
    ------A7
    ----------A4
    ------A7
    ----------A4
    ------A5
    ----------A4
      

  14.   

    如果要解决cdknet(cdksoft) 提出的问题,可以加上一个时候要素,因为可以确定:
    历史时间肯定小于现状时间的,这样的话,需要多加上一参数和一个字段
      

  15.   

    1。有一个表有2个子段。如下:
        历史       现状
        A1          A5
        A2          A5
        A3          A5
        A4          A6
        A4          A7
        A5          A8
        A6          A8
        A7          A8加一条:
        A8          A4     这种可能性会不会发现,发生了怎么办?(如果不发生当然不靠虑了)
      

  16.   

    还要问下,是不是指定从A8开如,如果是就简单了,还有,有没有A10 A3000 An???
      

  17.   

    杨兄:出现这样的结果,你大约是把:
    Select distinct 历史 from 表 where 现状=上级代码  order by 历史
    改成了?
    Select distinct * from 表 where 现状=上级代码  order by 历史
    吧?不能这样,*部份应该用:字段名1,字段名2,字段名3....  代替,用到几个字段就写几个
    这样才不会重复
      

  18.   

    我刚写完树形控件,我把我的代码给你参考参考,里面用了一个第归算法(不过,我的搜索和你的刚好相反,我是先找母级,再找它的子级):
    Private Sub FindUpdate(ByVal strBS As String, ByVal strValue As String)
        Dim tempRs As New ADODB.Recordset
        
        tempRs.Open "select * from xj_sb_lj where pid='" & strBS & "'", p_conn, a dOpenDynamic, adLockPessimistic
        If Not tempRs.EOF Then
            tempRs.MoveFirst
            While (Not tempRs.EOF)
                tempRs.Update "syzt", strValue
                Call FindUpdate(tempRs.Fields!bs, strValue)
                tempRs.MoveNext
            Wend
        Else
            Exit Sub
        End If
    End Sub
    Private Sub FindDel(ByVal strBS As String)
        Dim tempRs As New ADODB.Recordset
        
        tempRs.Open "select * from xj_sb_lj where pid='" & strBS & "'", p_conn, adOpenForwardOnly, adLockReadOnly
        If Not tempRs.EOF Then
            tempRs.MoveFirst
            While (Not tempRs.EOF)
                p_conn.Execute "delete from xj_sb_lj where bs='" & tempRs.Fields!bs & "'"
                Call FindDel(tempRs.Fields!bs)
                tempRs.MoveNext
            Wend
        Else
            'Exit Sub
            p_conn.Execute "delete from xj_xjnr where lx_bs='" & strBS & "'"
        End If
    End Sub
      

  19.   

    cdknet(cdksoft),是从A8开始.其实A8是用户指定的.将来可能有A100之类的等等
      

  20.   

    谢谢wbtanwf(学无止境) .我看看先
      

  21.   

    //得到当前node的子nodes
    public static void GetNodes(TreeNode node,string conditions,char level)
    {
    try
    {
    myNode[] mynode=new myNode[10000];//定义保存起始值的结构数组
    string str=@"select DeptName,DeptCode from Info where Level='"+level+"'and DeptCode like '"+conditions+"%'";
    SqlCommand myCommand = new SqlCommand ( str , globalVar.myConnection ) ;
    SqlDataReader reader=myCommand.ExecuteReader();
    long sum=0;
    while(reader.Read())
    {
    mynode[sum].DeptName=reader[0].ToString().Trim();
    mynode[sum].DeptCode=reader[1].ToString().Trim();
    sum++;
    }
    reader.Close();
    for(long i=0;i<sum;i++)
    {
    string name=mynode[i].DeptName.ToString();
    string code=mynode[i].DeptCode.ToString();
    TreeNode newNode=new TreeNode(name+"("+code+")");
    node.Nodes.Add(newNode);
    GetNodes(newNode,mynode[i].DeptCode,Convert.ToChar(level+1));//继续下一级的菜单
    }
    }
    catch(Exception e1)
    {
    MessageBox.Show(e1.Message,"提示");
    }
      

  22.   


    '建立树型结构:
    Private Sub CreateTree()
        Dim Key As String
        Dim Rs As ADODB.Recordset
        
        Set TreeNode = tvwArea.Nodes.Add(, , TreeRoot, "数据表", "iRoot")
        TreeNode.Expanded = True
        tStr = "select distinct 现状 from 表"
        Set Rs = WinApp.DBbase.Execute(tStr)
        For i = 0 To Rs.RecordCount - 1
            tStr = Trim(Rs(0))
            Key = i + 1 & Trim(Rs(0))
            Set TreeNode = tvwArea.Nodes.Add(TreeRoot, tvwChild, Key, tStr, "iDir", "iOpenDir")
            
            AddNodes Key
            Rs.MoveNext
        Next
        Rs.Close
        Set Rs = Nothing
        'tvwArea.Nodes(1).Selected = True
        'Call tvwArea_NodeClick(tvwArea.Nodes(1))
    End Sub'添加树型控件数据:
    Private Sub AddNodes(Keys As String)
    On Error GoTo ErrorHand
        Dim keyCount As Long
        Dim tNode As Node
        Dim Rs As New Recordset
        Dim NKeys As String, SQLStr As String, tStr As String
        keyCount = 1
        SQLStr = "select 历史 from 表 where 现状='" & Mid(Keys, 2) & "'"
        Set Rs = WinApp.DBbase.Execute(SQLStr)
        Do While Not Rs.EOF
            tStr = Trim(Rs(0))
            NKeys = keyCount & tStr
            
            Set tNode = tvwArea.Nodes.Add(Keys, tvwChild, NKeys, tStr)
            
            AddNodes keyCount              '嵌套循环
            Rs.MoveNext
            keyCount = keyCount + 1
        Loop
        Rs.Close
        Set Rs = Nothing
        Set tNode = Nothing
        Exit Sub
    ErrorHand:
        Set Rs = Nothing
        Set tNode = Nothing
    End Sub
      

  23.   

    注明:
        Set TreeNode = tvwArea.Nodes.Add(TreeRoot, tvwChild, Key, tStr, "iDir", "iOpenDir")   "iDir", "iOpenDir"   为图标
      

  24.   

    TreeRoot 为一常数,TreeRoot = "root"Set Rs = WinApp.DBbase.Execute(SQLStr) 执行一个SQL语句,并返回一个记录集
      

  25.   

    wjt2000(堂堂正正做男人),你给的什么呀?我晕
      

  26.   

    cdknet(cdksoft) ,让我仔细看一下.又点头大
      

  27.   

    先找出有多少现状,聚合所有的现状从第一个现状开始,找出它所有的建一个Node,把<<<现状>>>送到下面的循环{循环}
    查出所有的历史,如果有历史把找到的每一个历史写入一个Node,再把<<<历史>>>进行嵌套循环
    {循环}
     
      

  28.   

    cdknet(cdksoft) ,非常感谢你!我需要时间试一下.等我一下
      

  29.   

    http://expert.csdn.net/Expert/topic/1976/1976613.xml?temp=.4780542
      

  30.   

    代码中关于Key的设置有点不合理,我这里只考虑到了A1-A9,我只用一位数与名称组成Key,所以那里需要完善
      

  31.   

    虽然我也用Treevie1,但是我觉得烦