¿Cómo agregar nuevos elementos a una matriz?

291

Tengo el siguiente código:

String[] where;
where.append(ContactsContract.Contacts.HAS_PHONE_NUMBER + "=1");
where.append(ContactsContract.Contacts.IN_VISIBLE_GROUP + "=1");

Esos dos anexos no están compilando. ¿Cómo funcionaría eso correctamente?

Pentium10
fuente

Respuestas:

395

El tamaño de una matriz no se puede modificar. Si desea una matriz más grande, debe crear una instancia nueva.

Una mejor solución sería usar una ArrayListque pueda crecer según lo necesite. El método ArrayList.toArray( T[] a )le devuelve su matriz si la necesita en este formulario.

List<String> where = new ArrayList<String>();
where.add( ContactsContract.Contacts.HAS_PHONE_NUMBER+"=1" );
where.add( ContactsContract.Contacts.IN_VISIBLE_GROUP+"=1" );

Si necesita convertirlo en una matriz simple ...

String[] simpleArray = new String[ where.size() ];
where.toArray( simpleArray );

Pero la mayoría de las cosas que haces con una matriz también puedes hacerlas con esta ArrayList:

// iterate over the array
for( String oneItem : where ) {
    ...
}

// get specific items
where.get( 1 );
tangenos
fuente
99
¿De qué sirve usar Array si puede hacer lo mismo con ArrayList?
Skoua
@ tangens. Soy nuevo en Android, pero su respuesta me ayudó. Antes de encontrar la respuesta, perdí muchas horas
scott
1
Las matrices @Skoua son más eficientes. Predefinir el tamaño del objeto permite al compilador optimizar la memoria. Para algunas aplicaciones, es importante. Una pequeña aplicación que se ejecuta en una computadora moderna probablemente puede salirse con muchas listas antes de que la memoria se convierta en un problema.
DraxDomax
102

Use un List<String>, como un ArrayList<String>. Es dinámicamente cultivable, a diferencia de los arreglos (ver: Java 2nd Edition, Artículo 25: Prefiere listas a los arreglos ).

import java.util.*;
//....

List<String> list = new ArrayList<String>();
list.add("1");
list.add("2");
list.add("3");
System.out.println(list); // prints "[1, 2, 3]"

Si insiste en usar matrices, puede usar java.util.Arrays.copyOfpara asignar una matriz más grande para acomodar el elemento adicional. Sin embargo, esta no es la mejor solución.

static <T> T[] append(T[] arr, T element) {
    final int N = arr.length;
    arr = Arrays.copyOf(arr, N + 1);
    arr[N] = element;
    return arr;
}

String[] arr = { "1", "2", "3" };
System.out.println(Arrays.toString(arr)); // prints "[1, 2, 3]"
arr = append(arr, "4");
System.out.println(Arrays.toString(arr)); // prints "[1, 2, 3, 4]"

Esto es O(N)por append. ArrayList, por otro lado, ha O(1)amortizado el costo por operación.

Ver también

poligenelubricantes
fuente
Puede duplicar el tamaño de la matriz cada vez que la capacidad no sea suficiente. De esa forma se amortizará O (1). Probablemente lo que ArrayListhace internamente.
Siyuan Ren
32

Apache Commons Lang tiene

T[] t = ArrayUtils.add( initialArray, newitem );

devuelve una nueva matriz, pero si realmente está trabajando con matrices por alguna razón, esta puede ser la forma ideal de hacerlo.

xenoterracida
fuente
23

Hay otra opción que no he visto aquí y que no involucra objetos o colecciones "complejas".

String[] array1 = new String[]{"one", "two"};
String[] array2 = new String[]{"three"};
String[] array = new String[array1.length + array2.length];
System.arraycopy(array1, 0, array, 0, array1.length);
System.arraycopy(array2, 0, array, array1.length, array2.length);
ACLima
fuente
14

No hay método append()en matrices. En cambio, como ya se sugirió, un objeto List puede satisfacer la necesidad de insertar elementos dinámicamente, por ejemplo.

List<String> where = new ArrayList<String>();
where.add(ContactsContract.Contacts.HAS_PHONE_NUMBER + "=1");
where.add(ContactsContract.Contacts.IN_VISIBLE_GROUP + "=1");

O si realmente desea utilizar una matriz:

String[] where = new String[]{
    ContactsContract.Contacts.HAS_PHONE_NUMBER + "=1",
    ContactsContract.Contacts.IN_VISIBLE_GROUP + "=1"
};

pero este es un tamaño fijo y no se pueden agregar elementos.

Robert
fuente
Entonces, ¿una consulta parametrizada acepta también ArrayList como selectionArgs?
Skynet
7

Como dijeron los tangenos, el tamaño de una matriz es fijo. Pero primero debe crear una instancia, de lo contrario, será solo una referencia nula.

String[] where = new String[10];

Esta matriz puede contener solo 10 elementos. Por lo tanto, puede agregar un valor solo 10 veces. En su código está accediendo a una referencia nula. Por eso no funciona. Para tener una colección que crezca dinámicamente, use ArrayList.

Simón
fuente
7
String[] source = new String[] { "a", "b", "c", "d" };
String[] destination = new String[source.length + 2];
destination[0] = "/bin/sh";
destination[1] = "-c";
System.arraycopy(source, 0, destination, 2, source.length);

for (String parts : destination) {
  System.out.println(parts);
}
dforce
fuente
6

¡He hecho este código! ¡Funciona a las mil maravillas!

public String[] AddToStringArray(String[] oldArray, String newString)
{
    String[] newArray = Arrays.copyOf(oldArray, oldArray.length+1);
    newArray[oldArray.length] = newString;
    return newArray;
}

¡¡Espero que te guste!!

Ángel
fuente
5

Necesita usar una Lista de colecciones. No puede cambiar el tamaño de una matriz.

Paligulus
fuente
4

Si desea almacenar sus datos en una matriz simple como esta

String[] where = new String[10];

y desea agregarle algunos elementos como números, por favor, use StringBuilder, que es mucho más eficiente que concatenar cadenas.

StringBuilder phoneNumber = new StringBuilder();
phoneNumber.append("1");
phoneNumber.append("2");
where[0] = phoneNumber.toString();

Este es un método mucho mejor para construir su cadena y almacenarla en su matriz 'where'.

RMachnik
fuente
4

Agregar nuevos elementos a la matriz de cadenas.

String[] myArray = new String[] {"x", "y"};

// Convert array to list
List<String> listFromArray = Arrays.asList(myArray);

// Create new list, because, List to Array always returns a fixed-size list backed by the specified array.
List<String> tempList = new ArrayList<String>(listFromArray);
tempList.add("z");

//Convert list back to array
String[] tempArray = new String[tempList.size()];
myArray = tempList.toArray(tempArray);
Kris
fuente
1
Ah, ya veo, usaste la <code>etiqueta y esto tuvo problemas con los tipos genéricos. Intenta evitar esta etiqueta, ya que ... tiene problemas, y sangra tu código con 4 espacios en blanco para obtener el formato adecuado. Lo hice por tu pregunta :).
Tom
4

Hay muchas formas de agregar un elemento a una matriz. Puede usar una temperatura Listpara administrar el elemento y luego convertirlo nuevamente Arrayo puede usar eljava.util.Arrays.copyOf y combinarlo con genéricos para obtener mejores resultados.

Este ejemplo le mostrará cómo:

public static <T> T[] append2Array(T[] elements, T element)
{
    T[] newArray = Arrays.copyOf(elements, elements.length + 1);
    newArray[elements.length] = element;

    return newArray;
}

Para usar este método solo necesita llamarlo así:

String[] numbers = new String[]{"one", "two", "three"};
System.out.println(Arrays.toString(numbers));
numbers = append2Array(numbers, "four");
System.out.println(Arrays.toString(numbers));

Si desea fusionar dos matrices, puede modificar el método anterior de esta manera:

public static <T> T[] append2Array(T[] elements, T[] newElements)
{
    T[] newArray = Arrays.copyOf(elements, elements.length + newElements.length);
    System.arraycopy(newElements, 0, newArray, elements.length, newElements.length);

    return newArray;
}

Ahora puede llamar al método de esta manera:

String[] numbers = new String[]{"one", "two", "three"};
String[] moreNumbers = new String[]{"four", "five", "six"};
System.out.println(Arrays.toString(numbers));
numbers = append2Array(numbers, moreNumbers);
System.out.println(Arrays.toString(numbers));

Como mencioné, también puedes usar Listobjetos. Sin embargo, requerirá un pequeño truco para lanzarlo de esta manera:

public static <T> T[] append2Array(Class<T[]> clazz, List<T> elements, T element)
{
    elements.add(element);
    return clazz.cast(elements.toArray());
}

Ahora puede llamar al método de esta manera:

String[] numbers = new String[]{"one", "two", "three"};
System.out.println(Arrays.toString(numbers));
numbers = append2Array(String[].class, Arrays.asList(numbers), "four");
System.out.println(Arrays.toString(numbers));
Teocci
fuente
newArray[elements.length] = element;, ¿Te refieres newArray[elements.length - 1] = element;?
David Riccitelli
3

No tengo tanta experiencia en Java, pero siempre me han dicho que las matrices son estructuras estáticas que tienen un tamaño predefinido. Debe usar una ArrayList o un Vector o cualquier otra estructura dinámica.

npinti
fuente
2

puede crear una lista de arrays y usarla Collection.addAll()para convertir la matriz de cadenas a su lista de arrays

ratzip
fuente
2

Simplemente puedes hacer esto:

System.arraycopy(initialArray, 0, newArray, 0, initialArray.length);
Jason Ivey
fuente
2

Si realmente desea cambiar el tamaño de una matriz, puede hacer algo como esto:

String[] arr = {"a", "b", "c"};
System.out.println(Arrays.toString(arr)); 
// Output is: [a, b, c]

arr = Arrays.copyOf(arr, 10); // new size will be 10 elements
arr[3] = "d";
arr[4] = "e";
arr[5] = "f";

System.out.println(Arrays.toString(arr));
// Output is: [a, b, c, d, e, f, null, null, null, null]
Inhailed al horno
fuente
1

El tamaño de la matriz no se puede modificar. Si tiene que usar una matriz, puede usar:

System.arraycopy(src, srcpos, dest, destpos, length); 
Jiao
fuente
0

También es posible preasignar un tamaño de memoria suficientemente grande. Aquí hay una implementación simple de la pila: se supone que el programa genera 3 y 5.

class Stk {
    static public final int STKSIZ = 256;
    public int[] info = new int[STKSIZ];
    public int sp = 0; // stack pointer
    public void push(int value) {
        info[sp++] = value;
    }
}
class App {
    public static void main(String[] args) {
        Stk stk = new Stk();
        stk.push(3);
        stk.push(5);
        System.out.println(stk.info[0]);
        System.out.println(stk.info[1]);
    }
}
baz
fuente