Como converter NSMutableArray em NSArray em objetivo-c?
NSArray *array = mutableArray;
Como converter NSMutableArray em NSArray em objetivo-c?
NSArray *array = mutableArray;
Respostas:
NSArray *array = [mutableArray copy];
Copy
faz cópias imutáveis. Isso é bastante útil porque a Apple pode fazer várias otimizações. Por exemplo, enviar copy
para uma matriz imutável apenas retém o objeto e retorna self
.
Se você não usar coleta de lixo ou ARC, lembre-se de que -copy
retém o objeto.
copy
cria um NSArray normal e não um NSMutableArray?
NSArray
& NSMutableArray
, NSString
& NSMutableString
. Mas não por exemplo, NSViewController
que sempre contém estado mutável.
An NSMutableArray
é uma subclasse de, NSArray
portanto, você nem sempre precisará converter, mas se quiser garantir que a matriz não possa ser modificada, crie uma NSArray
das seguintes maneiras, dependendo se deseja ou não liberada automaticamente:
/* Not autoreleased */
NSArray *array = [[NSArray alloc] initWithArray:mutableArray];
/* Autoreleased array */
NSArray *array = [NSArray arrayWithArray:mutableArray];
EDIT: A solução fornecida por Georg Schölly é uma maneira melhor de fazê-lo e muito mais limpa, especialmente agora que temos o ARC e nem precisamos chamar autorelease.
Gosto das duas principais soluções:
NSArray *array = [NSArray arrayWithArray:mutableArray];
Ou
NSArray *array = [mutableArray copy];
A principal diferença que vejo neles é como eles se comportam quando mutableArray é nulo :
NSMutableArray *mutableArray = nil;
NSArray *array = [NSArray arrayWithArray:mutableArray];
// array == @[] (empty array)
NSMutableArray *mutableArray = nil;
NSArray *array = [mutableArray copy];
// array == nil
[mutableArray copy]
pode ser simplificado para [nil copy]
. No objetivo-c, qualquer mensagem enviada para zero será sempre nula. É importante lembrar a distinção entre "nada" e "uma matriz sem nada".
você tenta este código ---
NSMutableArray *myMutableArray = [myArray mutableCopy];
e
NSArray *myArray = [myMutableArray copy];
Abaixo está uma maneira de converter NSMutableArray em NSArray:
//oldArray is having NSMutableArray data-type.
//Using Init with Array method.
NSArray *newArray1 = [[NSArray alloc]initWithArray:oldArray];
//Make copy of array
NSArray *newArray2 = [oldArray copy];
//Make mutablecopy of array
NSArray *newArray3 = [oldArray mutableCopy];
//Directly stored NSMutableArray to NSArray.
NSArray *newArray4 = oldArray;
No Swift 3.0, há um novo tipo de dados Array . Declare Array usando a let
palavra-chave, então ele se tornará NSArray E se declarar usando a var
palavra-chave, ele se tornará NSMutableArray .
Código de amostra:
let newArray = oldArray as Array
No objetivo-c:
NSArray *myArray = [myMutableArray copy];
Em rápida:
var arr = myMutableArray as NSArray
NSArray *array = mutableArray;
este [mutableArray copy]
antipadrão está em todo o código de amostra. Pare de fazer isso para matrizes mutáveis descartáveis que são transitórias e desalocadas no final do escopo atual.
Não há como o tempo de execução otimizar a cópia desnecessária de uma matriz mutável que está prestes a sair do escopo, decretada para 0 e desalocada para sempre.
NSMutableArray
a uma NSArray
variável não o ocultará (que é a questão da OP). Expor esse valor (por exemplo, como um valor de retorno ou como uma propriedade) pode resultar em problemas de depuração muito difíceis se esse valor for alterado inesperadamente. Isso se aplica a mutações internas e externas, pois o valor mutável é compartilhado.
NSMutableArray
variável. Como o objeto nunca deixou de ser uma matriz mutável, a chamada de métodos de mutação terá êxito e mutará os dados compartilhados. Se, por outro lado, a matriz mutável original foi copiada - alterando-a para uma matriz imutável - e depois atribuída a uma NSMutableArray
variável e tivesse métodos de mutação chamados, essas chamadas falhariam com doesNotRespondToSelector
erros, porque o objeto que recebeu a chamada do método de mutação está em fato imutável e não responde a esses métodos.
Se você estiver construindo um array via mutabilidade e quiser retornar uma versão imutável, basta retornar o array mutável como um "NSArray" por herança.
- (NSArray *)arrayOfStrings {
NSMutableArray *mutableArray = [NSMutableArray array];
mutableArray[0] = @"foo";
mutableArray[1] = @"bar";
return mutableArray;
}
Se você "confia" no chamador para tratar o objeto de retorno (tecnicamente ainda mutável) como um NSArray imutável, esta é uma opção mais barata que [mutableArray copy]
.
Para determinar se ele pode alterar um objeto recebido, o destinatário de uma mensagem deve confiar no tipo formal do valor de retorno. Se receber, por exemplo, um objeto de matriz digitado como imutável, não deverá tentar mutá-lo . Não é uma prática de programação aceitável determinar se um objeto é mutável com base em sua associação à classe.
A prática acima é discutida em mais detalhes aqui:
Prática recomendada: retorne mutableArray.copy ou mutableArray se o tipo de retorno for NSArray
NSArray *array = [mutableArray copy];