正常に開始されるNSMutableArray
オブジェクト(保持、すべて合成)があり、addObject:
メソッドを使用して簡単にオブジェクトを追加できます。しかし、特定のインデックスのオブジェクトをそのNSMutableArray
の新しいインデックスに置き換えたい場合、それは機能しません。
例えば:
ClassA.h
:
@interface ClassA : NSObject {
NSMutableArray *list;
}
@property (nonatomic, copy, readwrite) NSMutableArray *list;
@end
ClassA.m
:
#import "ClassA.h"
@implementation ClassA
@synthesize list;
- (id)init
{
[super init];
NSMutableArray *localList = [[NSMutableArray alloc] init];
self.list = localList;
[localList release];
//Add initial data
[list addObject:@"Hello "];
[list addObject:@"World"];
}
// Custom set accessor to ensure the new list is mutable
- (void)setList:(NSMutableArray *)newList
{
if (list != newList)
{
[list release];
list = [newList mutableCopy];
}
}
-(void)updateTitle:(NSString *)newTitle:(NSString *)theIndex
{
int i = [theIndex intValue]-1;
[self.list replaceObjectAtIndex:i withObject:newTitle];
NSLog((NSString *)[self.list objectAtIndex:i]); // gives the correct output
}
ただし、変更はメソッド内でのみ有効です。他の方法から、
NSLog((NSString *)[self.list objectAtIndex:i]);
同じ古い値を与えます。
特定のインデックスで古いオブジェクトを新しいオブジェクトに実際に置き換えて、他のメソッド内からも変更を認識できるようにする方法を教えてください。
メソッドを次のように変更しましたが、結果は同じです:
-(void)updateTitle:(NSString *)newTitle:(NSString *)theIndex
{
int i = [theIndex intValue]-1;
NSMutableArray *localList = [[NSMutableArray alloc] init];
localList = [localList mutableCopy];
for(int j = 0; j < [list count]; j++)
{
if(j == i)
{
[localList addObject:newTitle];
NSLog(@"j == 1");
NSLog([NSString stringWithFormat:@"%d", j]);
}
else
{
[localList addObject:(NSString *)[self.list objectAtIndex:j]];
}
}
[self.list release];
//self.list = [localList mutableCopy];
[self setList:localList];
[localList release];
}
みんな助けてください:)
これはトリックを行います:
[myMutableArray replaceObjectAtIndex:index withObject:newObject];
さて、ここでいくつかの混乱があります。
変更可能にするために、新しく作成されたmutableCopy
のNSMutableArray
を取る必要はありません。すでに変更可能です。名前にヒントがあります。プロパティにcopy
のセマンティクスを設定したい場合にのみ、セッターでそれを行う必要があります(設定したので、もちろん正当な理由があるかもしれません)。ただし、更新されたupdateTitle
コードに示されているように実行する必要はないので、そうするとlocalList
がリークします。
また、self.list
を介したプロパティアクセスと、同じメソッドでのlist
の直接使用を組み合わせています。これは無効ではありませんが、アクセサメソッドが行うその他の処理がランダムにバイパスされることを意味するため、悪い習慣です。このようなプロパティでは、アクセサー自体またはself
でdealloc
exceptを介してすべてを実行するのが一般的です。 ivarに直接アクセスするinit
(これについては意見が異なるようです)にある可能性があります。
また、[self.list release]
を呼び出さないでください。プロパティアクセサーは呼び出し側に所有権を与えません。これを行うことは涙で終わる、私の言葉をマークします。
これのどれも本当の質問に答えません。それがあなたの変化が消える理由です。元のupdateTitle
コードは、私が見る限りこれを説明していません-動作するはずです。だから、どこかであなたがself.list = theOriginalList
を呼んでいるので、あなたの変更を取り消すのではないかと思う。
更新:
引数のためだけに、投稿したコードはおそらくmeantのように見えると思うものを投稿します。 updateTitle
にインデックスを渡すための文字列の使用は保存しましたが、この方法で行うことはwrong。それは数字なので、そのまま渡す必要があります。番号がテキストフィールドなどからのものであっても、それは呼び出し側の関心事です。クラスインターフェイスは番号を指定する必要があります。同様に、1ベースのインデックスから0ベースのインデックスへの明らかな変更。暗黙のうちにこの種のことをしないでください、それは歯の泣きと歯ぎしりのためのレシピです。
ClassA.h:
#import <Cocoa/Cocoa.h>
@interface ClassA : NSObject
{
NSMutableArray* list;
}
- (void) setList:(NSMutableArray*)newList;
- (void) updateTitle:(NSString*)newTitle forIndex:(NSString*)theIndex;
@property (nonatomic, copy, readwrite) NSMutableArray* list;
@end
ClassA.m:
#import "ClassA.h"
@implementation ClassA
@synthesize list;
- (id) init
{
if ( self = [super init] )
{
list = [[NSMutableArray alloc] init];
[list addObject:@"Hello "];
[list addObject:@"World"];
}
return self;
}
- (void) setList:(NSMutableArray*) newList
{
if ( list != newList )
{
[list release];
list = [newList mutableCopy];
}
}
- (void) updateTitle:(NSString*)newTitle forIndex:(NSString*)theIndex
{
int i = [theIndex intValue] - 1;
[self.list replaceObjectAtIndex:i withObject:newTitle];
}
- (void) dealloc
{
[list release];
[super dealloc];
}
@end
これにより、さまざまな問題が解決されますが、updateTitle
はほとんど同じであることに注意してください。これらすべてをドロップしても、変更がまだ生き残っていない場合は、list
をどこかで確実にリセットしています。
より簡単な答えは次のとおりです。
self.list[i] = newTitle;
これはちょうどのように動作します
[self.list replaceObjectAtIndex:i withObject:newTitle];
Swift=を試すことができます:
//if you have indexPath
self.readArray.removeAtIndex((indexPath?.row)!)
self.readArray.insert(tempDict, atIndex: (indexPath?.row)!)
//tempDict is NSDictionary object.
最後に完璧なコードを手に入れた、
let DuplicateArray: NSArray = array
let DuplicateMutableArray: NSMutableArray = []
DuplicateMutableArray.addObjectsFromArray(DuplicateArray as [AnyObject])
var dic = (DuplicateMutableArray[0] as! [NSObject : AnyObject])
dic["is_married"] = "false"
DuplicateMutableArray[self.SelectedIndexPath] = dic
array = []
array = (DuplicateMutableArray.copy() as? NSArray)!
//出力は次のようになります
array = [
{
"name": "Kavin",
"Age": 25,
"is_married": "false"
},
{
"name": "Kumar",
"Age": 25,
"is_married": "false"
}
]
この行を見てください:
@property (nonatomic, copy, readwrite) NSMutableArray *list;
copyは、self.listにアクセスするたびに、オブジェクトの「_list」インスタンス変数ではなく、そのリストのコピーを取得することを意味します。 [self.list replaceObjectAtIndex ...]と記述すると、リストのコピー内のオブジェクトを置き換えます。元の_listは変更されていません。使うだけ
@property (nonatomic, strong, readwrite) NSMutableArray *list;
混乱を避けるため、「list」インスタンス変数と@synthesizeステートメントを削除し、_listを使用してインスタンス変数にアクセスします。