Quel est le moyen le plus rapide d’ajouter un nouvel élément à un tableau existant?
Dim arr As Integer() = {1, 2, 3}
Dim newItem As Integer = 4
(Je sais déjà que lorsque vous travaillez avec une liste dynamique d'éléments, vous devriez plutôt utiliser un List
, ArrayList
ou similaire IEnumerables
. Mais que faire si vous êtes bloqué code qui utilise des tableaux?)
Ce que j'ai essayé jusqu'à présent:
' A) converting to List, add item and convert back
Dim list As List(Of Integer)(arr)
list.Add(newItem)
arr = list.ToArray()
' --> duration for adding 100.000 items: 33270 msec
' B) redim array and add item
ReDim Preserve arr(arr.Length)
arr(arr.Length - 1) = newItem
' --> duration for adding 100.000 items: 9237 msec
' C) using Array.Resize
Array.Resize(arr, arr.Length + 1)
arr(arr.Length - 1) = newItem
' --> duration for adding 100.000 items: 1 msec
' --> duration for adding 100.000.000 items: 1168 msec
A) semble très lent puisque chaque fois qu'un élément est ajouté, deux conversions de l'ensemble du tableau sont effectuées. B) semble plus rapide mais le tableau est quand même copié une fois pendant le ReDim Preserve
. C) semble être le plus rapide à ce stade. Y a-t-il quelque chose de mieux?
Le cas C) est le plus rapide. Ayant ceci comme une extension:
Public Module MyExtensions
<Extension()> _
Public Sub Add(Of T)(ByRef arr As T(), item As T)
Array.Resize(arr, arr.Length + 1)
arr(arr.Length - 1) = item
End Sub
End Module
Usage:
Dim arr As Integer() = {1, 2, 3}
Dim newItem As Integer = 4
arr.Add(newItem)
' --> duration for adding 100.000 items: 1 msec
' --> duration for adding 100.000.000 items: 1168 msec
Pour ceux qui ne savaient pas quoi faire ensuite, ajoutez simplement un nouveau fichier de module et insérez du code @jor (avec mon petit tableau hacké, prenant en charge le tableau 'Nothing') ci-dessous.
Module ArrayExtension
<Extension()> _
Public Sub Add(Of T)(ByRef arr As T(), item As T)
If arr IsNot Nothing Then
Array.Resize(arr, arr.Length + 1)
arr(arr.Length - 1) = item
Else
ReDim arr(0)
arr(0) = item
End If
End Sub
End Module
Dim arr As Integer() = {1, 2, 3}
Dim newItem As Integer = 4
ReDim Preserve arr (3)
arr(3)=newItem
pour plus d'informations Redim
Pas très propre mais ça marche :)
Dim arr As Integer() = {1, 2, 3}
Dim newItem As Integer = 4
arr = arr.Concat({newItem}).ToArray
Cela dépend de la fréquence à laquelle vous insérez ou lisez. Vous pouvez augmenter le tableau de plus d'un si nécessaire.
numberOfItems = ??
' ...
If numberOfItems+1 >= arr.Length Then
Array.Resize(arr, arr.Length + 10)
End If
arr(numberOfItems) = newItem
numberOfItems += 1
De plus, pour A, vous n’avez besoin que d’obtenir le tableau si nécessaire.
Dim list As List(Of Integer)(arr) ' Do this only once, keep a reference to the list
' If you create a new List everything you add an item then this will never be fast
'...
list.Add(newItem)
arrayWasModified = True
' ...
Function GetArray()
If arrayWasModified Then
arr = list.ToArray()
End If
Return Arr
End Function
Si vous avez le temps, je vous suggère de tout convertir en liste et de supprimer les tableaux.
* Mon code pourrait ne pas compiler