# Vectoren vs. "richtige" Arrays



## meez (7. Okt 2004)

Wie perfomant sind eigentlich Vectoren im Gegensatz zu "richtigen" Arrays...???:L 

Ein Vector ist ja auch ein Objectarray mit einer festen Startgrössen...Wird diese Grösse überschritten, so wird ein noch grösserer Objektarray erzeugt, und der Inhalt kopiert...:meld: 
Das scheint zeimlich unperformant, aber praktisch...

Hat da jemand Erfahrung, wies mit der Performance aussieht  :?:


----------



## Beni (7. Okt 2004)

Das Ereignis "vergrössern" wird im Vergleich zu den anderen Ereignissen "Object lesen" und "Object einschreiben" so selten aufgerufen, dass man keinen Unterschied bemerkt.


----------



## Sky (8. Okt 2004)

Beni hat gesagt.:
			
		

> Das Ereignis "vergrössern" wird im Vergleich zu den anderen Ereignissen "Object lesen" und "Object einschreiben" so selten aufgerufen, dass man keinen Unterschied bemerkt.



Diese Aussage ist viel zu allgemein gültig und ich denke, dass man sie so nicht stehen lassen kann.

Ein Vector wird mit der Größe 10 initialisiert und wächst um weitere 10 Elemente bei Bedarf (im Standardfall!). Wenn ich also den Fall nehme und 10.000 Elemente habe, dann wird ganz schön oft vergrößert!

Also: Wenn man vorher weiß, wie groß sein gewünschter Daten-Container minimum sein muss so sollte man das angeben; aber: ein großer Daten-Container braucht mehr Speicher als ein kleiner (auch im "leerem" Zustand!).

Wenn man also nicht aufpaßt, so kann der Vector ganz schön langsam werden. Außerdem ist der Vector dadurch, dass er "synchronized" ist eh schon mal ein wenig langsamer als z.B. eine ArrayList.

Des weiteren gilt zu beachten, dass ein "richtiges Array" schon typsicher ist: 

```
String[] s = new String[10];
    s[0] = new Integer[1];   // hier würde der Compiler schon meckern
    s[0] = new String("1");  // das hier geht
```

Dies ist aber bei einem Vector ist ab 1.5 so (aufgrund der Templates). In den JAVA-Versionen vor 1.5 muss man also die Objekte aus dem Vector ggfls. nochmal casten, wenn man Objekt-spezifische Operationen durchführen will. Und das kostet auch Zeit!

So, wenn noch Fragen sind, bitte melden 

Grüsse, Sky


----------



## Beni (8. Okt 2004)

> Ein Vector wird mit der Größe 10 initialisiert und wächst um weitere 10 Elemente bei Bedarf (im Standardfall!). Wenn ich also den Fall nehme und 10.000 Elemente habe, dann wird ganz schön oft vergrößert!


Im Standartfall wird die Grösse des Arrays verdoppelt (guck im Quellcode nach!), um von 10 auf 10'000 zu kommen, braucht es dann ganze 10 Vergrösserungen :wink:

Mit dem Rest bin ich einverstanden, aber im Normalfall ist ein Programm nicht aufgrund des leicht erhöhten Zugriffs auf ein Vector langsam... (du verstehst, was ich damit meine :bae: )


----------



## Sky (8. Okt 2004)

Beni hat gesagt.:
			
		

> Im Standartfall wird die Grösse des Arrays verdoppelt (guck im Quellcode nach!), um von 10 auf 10'000 zu kommen, braucht es dann ganze 10 Vergrösserungen :wink:


 Ok, ok, hast ja recht war'n Denkfehler.



			
				Beni hat gesagt.:
			
		

> Mit dem Rest bin ich einverstanden, aber im Normalfall ist ein Programm nicht aufgrund des leicht erhöhten Zugriffs auf ein Vector langsam... (du verstehst, was ich damit meine :bae: )


 Kann m.E. auch eine Ursache sein. Obwohl es natürlich auch viele, viele andere Faktoren gibt. Da hast Du recht!


----------



## meez (8. Okt 2004)

Es ist ehh schlecht, wenn man Vectoren mit 100000 Einträgen hat...
Da wird der Vector auch nicht mehr ins Gewicht fallen...


----------



## dotlens (8. Okt 2004)

was ist denn am besten für 100000 Einträge?


----------



## bygones (8. Okt 2004)

persönlich halte ich es auch für unsinnig einen Vector von 1.000.000 Einträge sich im Speicher zu halten - bei einer solchen größen sollten DBs ins Spiel kommen und man sollte nur das auslesen was auch prozessiert wird.

Allgmein gilt: Vectoren und ArrayListen haben den Nachteil des neu allozierens (wie schon erwähnt), aber sind u.a. weil sie Arrays sind dadurch vorteilhaft, dass man indexbasiert auf sie zugreifen kann.

Wenn man aber viel einfügen bzw. löschen muss bietet sich z.b. die LinkedList an - bei ihr entfällt das Array kopieren...


----------



## Guest (9. Okt 2004)

Wenn es nur um den Aufbau einer Liste geht (nur Hinzufügen mit add(...) und Lesen immer von Anfang bis Ende), 
dann ist LinkedList am schnellsten.
Vector würde ich nicht mehr verwenden. ArrayList ist besser und schneller.


----------



## meez (9. Okt 2004)

Anonymous hat gesagt.:
			
		

> Vector würde ich nicht mehr verwenden. ArrayList ist besser und schneller.



Grund/Quelle??


----------



## Guest (9. Okt 2004)

meez hat gesagt.:
			
		

> Grund/Quelle??


API und auch Oreilly's "Java Performance Tunning".
Laut der API sind fast alle Operation in Vector synchronized, während in 
ArrayList nicht. Wenn nicht gerade von mehreren Threads aus darauf
zugegriffen wird, dann kann man auf eine "synchronized" Variante ruhig verzichten.
Dies macht bei intensiver Nutzung der Collections ziemlich viel aus.
Mach' doch mal einen Test mit allen Typen von Collections, dann siehst Du,
was in Deinem Fall am schnellsten ist. Es ist immer wieder von der Anwendung
abhängig.


----------



## Reality (9. Okt 2004)

Vector ist ziemlich langsam da:

1. Man kann keine primitiven Typen speichern, sondern nur Objekte (trifft auch das ganze Collection Framework zu). Außer dass es langsam ist, entsteht auch viele MBs Datenmüll!
2. Es ist synchronized.

Wenn du primitive Datentypen speichern willst, dann würde ich mir eine Klasse schreiben, dass Arrays dynamisch vergrößert.
Und wenn du kein Multithreading verwendest, würde ich ArrayList oder LinkedList verwenden, da es nicht synchronized ist.

Liebe Grüße
Reality


----------



## Guest (9. Okt 2004)

Übrigens, das gleiche gilt für die Entscheidung Hashtable oder HashMap.
HashMap ist schneller aber nicht threadsafe.


----------



## stev.glasow (9. Okt 2004)

Reality hat gesagt.:
			
		

> Vector ist ziemlich langsam da:
> 
> 1. Man kann keine primitiven Typen speichern, sondern nur Objekte (trifft auch das ganze Collection Framework zu). Außer dass es langsam ist, entsteht auch viele MBs Datenmüll!
> 2. Es ist synchronized.
> ...



Ich denke nicht , dass LinkedList wesentlich schneller ist weil es nicht synchronized ist.
Vector arbeitet mit einem Object-Array, was einem einen schnelleren Zugriff über den Index erlaubt aber wenn man Daten oft einfügt  und der interne Array zu klein wird, muss ein neuer Array angelegt und der alte in diesen kopiert werden, was recht aufwendig ist.
LinkedList arbeitet hingegen als doppelt verkettete Liste, mit der man schnell Einfügen und Löschen kann (da das kopieren des Arrays entfällt) aber der Zugriff über den Index dauert darfür etwas länger. 
Sprich, was schneller ist, hängt von der Anwendung ab.

Und das solch eine selbst geschriebene Klasse so viel bringt kann ich mir nicht vorstellen. Hast du das mal irgendwie verglichen?


----------



## Reality (10. Okt 2004)

stevg hat gesagt.:
			
		

> Und das solch eine selbst geschriebene Klasse so viel bringt kann ich mir nicht vorstellen. Hast du das mal irgendwie verglichen?


Ca. 63 mal bei mir.
http://www.c-plusplus.de/forum/viewtopic.php?t=84460&start=20


----------



## foobar (10. Okt 2004)

Reality hat gesagt.:
			
		

> stevg hat gesagt.:
> 
> 
> 
> ...



Das ist aber keine verkettete Liste. Ein verkette Liste sieht ungefähr so aus:

```
public class PrimitivArrayList
{
	private ListElement firstElement, lastElement;
	private int amountElements;
	public PrimitivArrayList()
	{
		this.firstElement = new ListElement(0, -1, null);
		this.lastElement = this.firstElement;
	}
	
	private ListElement getElementAt(int index, int currentpos, ListElement element)
	{
		return currentpos == index ? element : getElementAt(index, ++currentpos, element.getNext());
	}
	
	public int get(int index)
	{
		return index >= this.getSize() ? -1 : getElementAt(index, 0, this.firstElement).getValue();
	}
	
	private void print(ListElement element)
	{
		System.out.println(element);
		ListElement next = element.getNext();
		if (next != null)
		{
			print(next);
		}
	}
	
	public void add(int item)
	{
		if (firstElement.getValue() == -1)
		{
			firstElement.setValue(item);
		}
		else
		{
			ListElement newElement = new ListElement(lastElement.getPosition() + 1, item, null);
			lastElement.setNext(newElement);
			this.lastElement = newElement;
		}
		amountElements++;
	}
	
	public void printAll()
	{
		print(firstElement);
	}
	
	public int getSize()
	{
		return this.amountElements;
	}
	
	private class ListElement
	{
		private int value;
		private ListElement next;
		private int position;
		public ListElement(int position, int value, ListElement next)
		{
			this.position = position;
			this.value = value;
			this.next = next;
		}
		public ListElement getNext()
		{
			return next;
		}
		public int getValue()
		{
			return value;
		}
		public void setNext(ListElement element)
		{
			next = element;
		}
		public void setValue(int i)
		{
			value = i;
		}
		public int getPosition()
		{
			return position;
		}
		public void setPosition(int i)
		{
			position = i;
		}
		public String toString()
		{
			return this.getClass() + " position " + this.getPosition() + " value " + this.getValue();
		}
	}
	
	public static void main(String[] args)
	{
		PrimitivArrayList list = new PrimitivArrayList();
		list.add(1);
		list.add(2);
		list.add(3);
		list.add(4);
		list.printAll();
	}
}
```


----------



## Roar (10. Okt 2004)

Reality hat gesagt.:
			
		

> http://www.c-plusplus.de/forum/viewtopic.php?t=84460&start=20



 :applaus:  :applaus:  :toll:  :toll:


----------



## Reality (10. Okt 2004)

Roar hat gesagt.:
			
		

> Reality hat gesagt.:
> 
> 
> 
> ...



Jojo. :bae: 
Sach mal, was los?


----------



## Roar (10. Okt 2004)

ich find den thread gut, bzw. deine beiträge


----------

