Nasıl artan sırada bir ikili arama ağacı düğüm elemanlı bir dizi doldurmak için?

oy
0

Bir okul ödevi ben ascendig sırayla düğüm elemanı dizisi dönmelidir bir yöntem tamamlamak gerekiyor. düğümleri Ben işi yapmak için bir özyinelemeli yöntemini oluşturmak için bir ipucu var, bu yüzden doğru sıralamak için, bir ikili arama ağacında monte ediliyor.

Sorun, bu da bir test çıkışına göre koleksiyonunda tüm öğeleri elde olmamasıdır (java.lang.AssertionError. toArray () koleksiyonunda tüm öğeleri döndürmez)

Ben diziye başa başka yol ile gelip olamazdı ve ben özyineleme bile çalışır eğer tam olarak emin değilim. Herhangi bir yardım çok takdir edilmektedir. Aşağıda benim kodudur:

public class BinarySearchTree<E extends Comparable<E>> implements
    IfiCollection<E> {

    Node root;
    Node current;
    int size = 0;
    int i = 0;

    public class Node {
    E obj;
    Node left, right;

    public Node(E e) {
        obj = e;
    }

    } // END class Node

    [...]

    public E[] toArray(E[] a) {

    Node n = root;

    a = sort(n, a);
    return a;

    }

    public E[] sort(Node n, E[] a) { //, int idx, E[] a) {

    if (n.left != null) {
        current = n.left;
        sort(current, a);
    }


    a[i] = current.obj;
    i++;

    if (n.right != null) {
        current = n.right;
        sort(current, a);
        }

    return a;

    } // END public Node sort

    [...]

} // END class BinarySearchTree

Deney çıkışı:

java.lang.AssertionError. toArray () koleksiyonu .: TestPerson ( Bender) olarak compareTo (TestPerson ( Fry)) == 0 beklenen tüm unsurları döndürmez: true ama oldu: inf1010.assignment de yanlış inf1010.assignment.IfiCollectionTest.toArray de inf1010.assignment.IfiCollectionTest.assertCompareToEqualsNoOrder (IfiCollectionTest.java:100) de inf1010.assignment.IfiCollectionTest.assertCompareToEquals (IfiCollectionTest.java:83) en .IfiCollectionTest.assertCompareToEquals (IfiCollectionTest.java:74) ( IfiCollectionTest.java:202)

protected void assertCompareToEquals(TestPerson actual,
        TestPerson expected, String msg) {
            assertTrue(actual.compareTo(expected) == 0, String.format( // l:74
            %s: %s.compareTo(%s) == 0, msg, actual, expected));
}

    [...]

protected void assertCompareToEquals(TestPerson[] actual,
        TestPerson[] expected, String msg) {
    for (int i = 0; i < actual.length; i++) {
        TestPerson a = actual[i];
        TestPerson e = expected[i];
        assertCompareToEquals(a, e, msg); // l:83
    }
}

    [...]

protected void assertCompareToEqualsNoOrder(TestPerson[] actual,
        TestPerson[] expected, String msg) {
    assertEquals(actual.length, expected.length, msg);

    TestPerson[] actualElements = new TestPerson[actual.length];
    System.arraycopy(actual, 0, actualElements, 0, actual.length);

    TestPerson[] expectedElements = new TestPerson[expected.length];
    System.arraycopy(expected, 0, expectedElements, 0, expected.length);

    Arrays.sort(expectedElements);
    Arrays.sort(actualElements);

    assertCompareToEquals(actualElements, expectedElements, msg); // l:100
}

    [...]

@Test(dependsOnGroups = { collection-core },
    description=Tests if method toArray yields all the elements inserted in the collection in sorted order with smallest item first.)
public void toArray() {
    TestPerson[] actualElements = c.toArray(new TestPerson[c.size()]);

    for (int i = 0; i < actualElements.length; i++) {
        assertNotNull(actualElements[i],
                toArray() - array element at index  + i +  is null);
    }

    TestPerson[] expectedElements = allElementsAsArray();
    assertCompareToEqualsNoOrder(actualElements, expectedElements, // l:202
            toArray() does not return all the elements in the collection.);

    Arrays.sort(expectedElements);
    assertCompareToEquals(actualElements, expectedElements,
            toArray() does not return the elements in sorted order with 
                    + the smallest elements first.);


    TestPerson[] inArr = new TestPerson[NAMES.length + 1];
    inArr[NAMES.length] = new TestPerson(TEMP);
    actualElements = c.toArray(inArr);
    assertNull(actualElements[NAMES.length],
            The the element in the array immediately following the 
            + end of the list is not set to null);
}

Ben, bu oldukça geniş olduğunu Test kodunun daha gönderilmesi gerekiyor eğer bilmiyorum ve bir yazı için biraz fazla olabilir?

Oluştur 18/03/2011 saat 13:02
kaynak kullanıcı
Diğer dillerde...                            


4 cevaplar

oy
0

Ben nereye karıştı nasıl bir ikili arama ağacı çalışmalarını kontrol eğer, her zaman sıralandığını olduğunu düşünüyorum. Eğer kök düğümde başlar ve yeni bir düğüm eklemek olarak o zaman, değerlerine bağlı (sağına veya soluna yani) uygun pozisyona ekler. Yani başlamak için sıralama aramak zorunda olmamalıdır. Bu yüzden orada başlatın ve ikili arama ağaçları da okumaya. Örneğin wikipedia iyi bir makale var.

Güncelleme: Ya bunu yapmak gerekmez yorumumu geçiyoruz. Eğer bu sırayla ağaca 8, 3, 7, 9, 12, 2, 10, 1 insert düşünelim. Böyle görsterme olmalıdır:

      8
     / \
    3   9
   / \   \
  2   7   12
 /       /
1       10

Eğer bakarsan o, sırayla onları almak kökünde başlar, daha sonra sola doğru var sola bir düğüm varsa, değilse, kendisini dönmek ve bir değeri varsa sağa gitmek demektir. Karşılaştığınız her düğüm için bu tekrarlamak.

Cevap 18/03/2011 saat 13:30
kaynak kullanıcı

oy
1

Sana kod var bakın

if (n.left != null) {
        current = n.left;
        sort(current, a);
  }

ama ne zaman hangi noktada geçerli düğümün geçerli arkasını ayarlamak işaret biçimde bulmak gibi olamaz

a[i] = current.obj;

Doğru sonuç almak. Tüm sonuç almadığınız ihtimal bu yüzden. Geçerli ihtiyaçları sınıf değişken olabilir ve sadece sıralama yönteminde bildirilmedi için neden Her durumda ben (kod parçaları en azından Yayınladığınız) görmüyorum. Genel olarak gerçekten yok bunları gerekirse sınıf değişkenleri kullanarak olmamalıdır.

Düzenleme: Ya geri düğüme akım ayarlayabilirsiniz böyle sol çocuğa tür çağrıldıktan sonra işliyoruz

current = n;
a[i] = current.obj;
i++;

Ya da hiç akım kullanan bu durumda böyle bir şey olurdu değil

if (n.left != null)
    sort(n.left, a);
a[i] = n.obj;
i++;
if (n.right != null)
    sort(n.right, a);
Cevap 18/03/2011 saat 13:57
kaynak kullanıcı

oy
0

http://cs.armstrong.edu/liang/intro8e/html/BinaryTree.html

Aradığınız şeyi yapmak kolay yolu inorder ağaç travers ve bir ArrayList eklemektir. ArrayList .toArray () yöntemini çağırabilirsiniz diziyi almak için.

Bir ArrayList'deki kullanamıyorsanız, bir dizin ve inordertraversal ve artım dışında bir diziyi bildirmek, kendi diziyi bildirmek için ağaçta kaç unsurlar bilmesi gerekir.

sözde kod:

variables:
arraysize = root.count()
E[] inOrderNodeArray = new E[arraysize]
int index = 0

inorder traversal:
void inorder(Node n) {
    if (n) {
        inorder(n.left)
        inOrderNodeArray[index] = n
        index++
        inorder(n.right)
    }
}
Cevap 18/03/2011 saat 14:01
kaynak kullanıcı

oy
1

Tamam, sorun "küresel" değişkeni kullanmanızın olduğunu düşünüyorum current. O ayarlanır yolu, çok mantıklı değil. "Geçerli", çünkü zaten gerek yok Nodeparametrelerinde sağlanan biridir.

Ayrıca size fonksiyonunu yeniden adlandırma düşünmelisiniz. Sadece ağacın içeriğini toplayarak şey burada tasnif değildir, bu yüzden bir ad gibi collectdaha uygun olacaktır.

public E[] toArray(E[] a) {
  Node n = root;
  a = collect(n, a);
  return a;
}

public E[] collect(Node n, E[] a) {

  if (n.left != null) {
    // If there is a left (smaller) value, we go there first
    collect(n.left, a);
  }


  // Once we've got all left (smaller) values we can
  // collect the value of out current Node.
  a[i] = n.obj;
  i++;

  if (n.right != null) {
    // And if there is a right (larger) value we get it next
    collect(n.right, a);
  }

  return a;
}

(Yasal Uyarı: Bu test değil)


Küresel endeks olmadan Alternatif uygulama:

public E[] toArray(E[] a) {
  Node n = root;
  collect(n, a, 0);
  return a;
}

public int collect(Node n, E[] a, int i) {

  if (n.left != null) {
    // If there is a left (smaller) value, we go there first
    i = collect(n.left, a, i);
  }


  // Once we've got all left (smaller) values we can
  // collect the value of out current Node.
  a[i] = n.obj;
  i++;

  if (n.right != null) {
    // And if there is a right (larger) value we get it next
    i = collect(n.right, a, i);
  }

  return i;
}
Cevap 18/03/2011 saat 14:07
kaynak kullanıcı

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more