int[] x = new int [] { 1, 2, 3};
int[] y = new int [] { 4, 5 };
int[] z = // your answer here...
Debug.Assert(z.SequenceEqual(new int[] { 1, 2, 3, 4, 5 }));
Agora eu uso
int[] z = x.Concat(y).ToArray();
Existe um método mais fácil ou mais eficiente?
Respostas:
fonte
params
parâmetros de número variável .System.IO.Directory.GetFiles()
retorna uma matriz de strings.Tente o seguinte:
fonte
List<int> list = new List<int>(x);
Você pode escrever um método de extensão:
Então:
fonte
Copy
mais rápido queCopyTo
? Cuidado ao elaborar?Eu decidi por uma solução de uso geral que permite concatenar um conjunto arbitrário de matrizes unidimensionais do mesmo tipo. (Eu concatenava 3 ou mais de cada vez.)
Minha função:
E uso:
fonte
params T[][]
parathis T[][]
torná-lo uma extensão.É isso:
fonte
int[] result = array1.ToList().Concat(array2.ToList()).toArray();
você não pode aplicar o Concat em matrizes diretamente, acreditotoArray()
Cannot implicitly convert type 'System.Collections.Generic.IEnumerable<string>' to 'string[]'. An explicit conversion exists (are you missing a cast?)
int[] result = ?
, você está escondendo o problema de sua resposta atrás do seuvar
, pois seu resultado seráIEnumerable<int>
, nãoint[]
. (uma das razões pelas quais eu não gostovar
em retornos de métodos) #.ToArray()
chamada, esse código não retornará uma matriz real, portanto, também é uma resposta incorreta.Você pode atender a chamada ToArray () no final. Existe uma razão para você precisar que ela seja uma matriz após a chamada para a Concat?
Chamar o Concat cria um iterador sobre as duas matrizes. Ele não cria uma nova matriz, portanto você não usou mais memória para uma nova matriz. Quando você chama o ToArray, na verdade, cria uma nova matriz e ocupa a memória da nova matriz.
Portanto, se você apenas iterar facilmente os dois, basta ligar para a Concat.
fonte
Eu sei que o OP estava levemente curioso sobre o desempenho. Matrizes maiores podem ter um resultado diferente (consulte @kurdishTree). E que isso geralmente não importa (@ jordan.peoples). No entanto, fiquei curioso e, portanto, enlouqueci (como o @TigerShark estava explicando) .... quero dizer que escrevi um teste simples com base na pergunta original .... e todas as respostas ....
O resultado foi:
Role suas próprias vitórias.
fonte
CopyTo
será o mais rápido e ~ 3x mais rápido queRoll your own
.Tenha cuidado com o
Concat
método. A concatenação de matriz pós em C # explica que:Será ineficiente para matrizes grandes. Isso significa que o
Concat
método é apenas para matrizes de tamanho médio (até 10000 elementos).fonte
fonte
Mais eficiente (mais rápido) para usar
Buffer.BlockCopy
maisArray.CopyTo
,Eu escrevi um programa de teste simples que "aquece o Jitter", compilado no modo de lançamento e o executava sem um depurador conectado, na minha máquina.
Para 10.000.000 iterações do exemplo na pergunta
Se eu alterar as matrizes de teste para duas sequências de 0 a 99, obtive resultados semelhantes a este,
A partir desses resultados, posso afirmar que os métodos
CopyTo
eBlockCopy
são significativamente mais eficientesConcat
e, além disso, se o desempenho é uma meta,BlockCopy
têm valor acimaCopyTo
.Para ressaltar esta resposta, se o desempenho não importa, ou haverá poucas iterações, escolha o método que você achar mais fácil.
Buffer.BlockCopy
oferece algum utilitário para a conversão de tipos além do escopo desta pergunta.fonte
Resposta atrasada :-).
fonte
A estrutura mais eficiente em termos de RAM (e CPU) para armazenar a matriz combinada seria uma classe especial que implementa IEnumerable (ou se você desejar derivar da matriz) e vincula internamente às matrizes originais para ler os valores. O AFAIK Concat faz exatamente isso.
No seu código de exemplo, você pode omitir o .ToArray (), o que o tornaria mais eficiente.
fonte
Desculpe reviver um tópico antigo, mas e quanto a isso:
Então no seu código:
Até que você chame
.ToArray()
,.ToList()
ou.ToDictionary(...)
a memória não seja alocada, você pode "construir sua consulta" e chamar um desses três para executá-lo ou simplesmente passar por todos eles usando aforeach (var i in z){...}
cláusula que retorna um item de cada vez doyield return t;
acima...A função acima pode ser transformada em uma extensão da seguinte maneira:
Portanto, no código, você pode fazer algo como:
O resto é o mesmo de antes.
Uma outra melhoria para este seria mudar
T[]
paraIEnumerable<T>
(de modo aparams T[][]
se tornariaparams IEnumerable<T>[]
) fazer essas funções aceitarem mais do que apenas matrizes.Espero que isto ajude.
fonte
Você pode fazer isso da maneira que você se referiu ou, se quiser ser realmente manual, poderá fazer seu próprio loop:
fonte
Encontrei uma solução elegante de uma linha usando a expressão LINQ ou Lambda , ambas funcionam da mesma forma (o LINQ é convertido em Lambda quando o programa é compilado). A solução funciona para qualquer tipo de matriz e para qualquer número de matrizes.
Usando LINQ:
Usando o Lambda:
Eu forneci ambos pela preferência. Em termos de desempenho, as soluções @Sergey Shteyn ou @ deepee1 são um pouco mais rápidas, sendo a expressão Lambda a mais lenta. O tempo gasto depende do (s) tipo (s) de elementos da matriz, mas, a menos que haja milhões de chamadas, não há diferença significativa entre os métodos.
fonte
O que você precisa lembrar é que, ao usar o LINQ, você está utilizando a execução atrasada. Os outros métodos descritos aqui funcionam perfeitamente, mas são executados imediatamente. Além disso, a função Concat () provavelmente é otimizada de maneiras que você não pode fazer sozinho (chamadas para APIs internas, chamadas de SO etc.). De qualquer forma, a menos que você realmente precise otimizar, você está atualmente no seu caminho para "a raiz de todo mal";)
fonte
Tente o seguinte:
fonte
Aqui está a minha resposta:
Este método pode ser usado no nível de inicialização, por exemplo, para definir uma concatenação estática de matrizes estáticas:
No entanto, ele vem com duas advertências que você precisa considerar:
Concat
método cria um iterador sobre as duas matrizes: não cria uma nova matriz, sendo eficiente em termos de memória utilizada: no entanto, o subsequenteToArray
negará essa vantagem, pois na verdade criará uma nova matriz e ocupará a memória para o nova matriz.Concat
seria bastante ineficiente para matrizes grandes: deve ser usada apenas para matrizes de tamanho médio.Se apontar para o desempenho é uma obrigação, o método a seguir pode ser usado:
Ou (para fãs de one-liners):
Embora o último método seja muito mais elegante, o primeiro é definitivamente melhor para o desempenho.
Para informações adicionais, consulte este post no meu blog.
fonte
Para int [] o que você fez parece bom para mim. a resposta do astander também funcionaria bem
List<int>
.fonte
Para matrizes menores <10000 elementos:
fonte
Penso que a solução acima é mais geral e mais leve do que as outras que vi aqui. É mais geral porque não limita a concatenação para apenas duas matrizes e é mais leve porque não usa LINQ nem List.
Observe que a solução é concisa e a generalidade adicionada não adiciona uma sobrecarga significativa no tempo de execução.
fonte
int [] x = novo int [] {1, 2, 3}; int [] y = novo int [] {4, 5};
int [] z = x.União (y) .ToArray ();
fonte
Union
não é uma maneira muito boa de fazer isso, pois chamaDistinct
e remove implicitamente quaisquer duplicatas da coleção unida.Concat
é muito melhor, mas já está na pergunta original.fonte