আমি আমার উদ্দেশ্য-সি প্রোগ্রামে একটি সারি ডেটা কাঠামো ব্যবহার করতে চাই। সি ++ এ আমি এসটিএল সারিটি ব্যবহার করতাম। অবজেক্টিভ-সি সমতুল্য ডেটা স্ট্রাকচার কী? আমি কীভাবে পপ / পপ আইটেমগুলি ঠেকাতে পারি?
আমি আমার উদ্দেশ্য-সি প্রোগ্রামে একটি সারি ডেটা কাঠামো ব্যবহার করতে চাই। সি ++ এ আমি এসটিএল সারিটি ব্যবহার করতাম। অবজেক্টিভ-সি সমতুল্য ডেটা স্ট্রাকচার কী? আমি কীভাবে পপ / পপ আইটেমগুলি ঠেকাতে পারি?
উত্তর:
বেনের সংস্করণটি একটি সারির পরিবর্তে একটি স্ট্যাক, তাই আমি এটি কিছুটা টুইট করেছি:
NSMutableArray + + QueueAdditions.h
@interface NSMutableArray (QueueAdditions)
- (id) dequeue;
- (void) enqueue:(id)obj;
@end
NSMutableArray + + QueueAdditions.m
@implementation NSMutableArray (QueueAdditions)
// Queues are first-in-first-out, so we remove objects from the head
- (id) dequeue {
// if ([self count] == 0) return nil; // to avoid raising exception (Quinn)
id headObject = [self objectAtIndex:0];
if (headObject != nil) {
[[headObject retain] autorelease]; // so it isn't dealloc'ed on remove
[self removeObjectAtIndex:0];
}
return headObject;
}
// Add to the tail of the queue (no one likes it when people cut in line!)
- (void) enqueue:(id)anObject {
[self addObject:anObject];
//this method automatically adds to the end of the array
}
@end
আপনি নিজের নতুন পদ্ধতিগুলি যেখানেই ব্যবহার করতে চান সেখানে কেবল .h ফাইলটি আমদানি করুন এবং আপনার যেমন কোনও NSMutableArray পদ্ধতি আছে তেমন কল করুন।
শুভকামনা এবং কোডিং চালিয়ে যান!
আমি এটি বলব না যে এনএসমিটেবালারি ব্যবহার করা অগত্যা সর্বোত্তম সমাধান, বিশেষত যদি আপনি বিভাগগুলির সাথে পদ্ধতিগুলি যুক্ত করছেন, ভঙ্গুরতার কারণে তারা যদি পদ্ধতির নামগুলির সাথে সংঘটিত হয় তবে তা ঘটতে পারে। দ্রুত-এন-নোংরা কাতারের জন্য, আমি কোনও পরিবর্তনীয় অ্যারের শেষে যুক্ত এবং সরানোর পদ্ধতিগুলি ব্যবহার করব। তবে, আপনি যদি সারিটি পুনঃব্যবহার করার পরিকল্পনা করেন বা আপনি যদি নিজের কোডটি আরও পঠনযোগ্য এবং স্ব-স্পষ্টরূপে দেখতে চান তবে একটি উত্সর্গীকৃত সারির শ্রেণি সম্ভবত আপনি চান is
কোকোতে একটি অন্তর্নির্মিত নেই, তবে অন্যান্য বিকল্প রয়েছে, এবং আপনাকে স্ক্র্যাচ থেকে একটিও লিখতে হবে না। সত্যিকারের সারির জন্য যা কেবল প্রান্তগুলি থেকে যোগ এবং সরিয়ে দেয়, একটি বিজ্ঞপ্তি বাফার অ্যারে একটি অত্যন্ত দ্রুত বাস্তবায়ন। সিএইচডিটাস্ট্রাকচারস.ফ্রেমেওয়ার্ক , ওপজেক্টিভ -সি-তে একটি লাইব্রেরি / ফ্রেমওয়ার্ক যা আমি কাজ করছি Check এটা তোলে সারিগুলি, সেইসাথে স্ট্যাকগুলি, deques, সাজানো সেট, ইত্যাদি আপনার উদ্দেশ্যে এর বাস্তবায়নের বিভিন্ন আছে, CHCircularBufferQueue উল্লেখযোগ্যভাবে দ্রুততর (অর্থাত benchmarks সঙ্গে প্রতিপাদ্য) এবং আরো পাঠযোগ্য (বোঝা যাচ্ছে যে নেতারা বিষয়ী) একজন NSMutableArray ব্যবহার করে।
সি ++ এসটিএল ক্লাসের পরিবর্তে নেটিভ অবজেক্টিভ-সি ক্লাস ব্যবহারের একটি বড় সুবিধা হ'ল এটি কোকো কোডের সাথে নির্বিঘ্নে সংহত করে এবং এনকোড / ডিকোড (সিরিয়ালাইজেশন) এর সাথে আরও ভালভাবে কাজ করে। এটি আবর্জনা সংগ্রহ এবং দ্রুত গণনার সাথে পুরোপুরি কাজ করে (উভয়ই 10.5+ তে উপস্থিত থাকে তবে কেবলমাত্র আইফোনে উপস্থিত) এবং আপনাকে কোন উদ্দেশ্য-সি অবজেক্ট এবং কোন সি ++ অবজেক্ট কী তা নিয়ে চিন্তা করতে হবে না।
সর্বশেষে, যদিও উভয় প্রান্ত থেকে যুক্ত এবং অপসারণের সময় এনএসমিটেবলআরারি একটি স্ট্যান্ডার্ড সি অ্যারের চেয়ে ভাল তবে এটি কোনও সারিটির জন্য দ্রুততম সমাধানও নয়। বেশিরভাগ অ্যাপ্লিকেশনগুলির জন্য এটি সন্তোষজনক তবে আপনার যদি গতির প্রয়োজন হয় তবে একটি বৃত্তাকার বাফার (বা কিছু ক্ষেত্রে ক্যাশে লাইনগুলিকে গরম রাখতে অনুকূলিত কোনও লিঙ্কযুক্ত তালিকা) সহজেই একটি এনএসমিটেবলআরিকে সঙ্কুচিত করতে পারে।
যতদূর আমি জানি, অবজেক্টিভ-সি কোনও সারি ডাটা স্ট্রাকচার সরবরাহ করে না। আপনার সেরা বাজি একটি তৈরি করা NSMutableArray
, এবং তারপর ব্যবহার [array lastObject]
, [array removeLastObject]
আইটেম আনতে, এবং [array insertObject:o atIndex:0]
...
আপনি যদি এটি অনেক কিছু করে থাকেন তবে NSMutableArray
ক্লাসের কার্যকারিতা বাড়িয়ে দিতে আপনি একটি উদ্দেশ্য-সি বিভাগ তৈরি করতে চাইতে পারেন । বিভাগগুলি আপনাকে বিদ্যমান ক্লাসগুলিতে গতিশীলভাবে ফাংশন যুক্ত করতে দেয় (এমনকি আপনার কাছে যার উত্স নেই) - আপনি এটির মতো একটি সারি তৈরি করতে পারেন:
(দ্রষ্টব্য: এই কোডটি আসলে একটি স্ট্যাকের জন্য, একটি সারি নয় below নীচের মন্তব্য দেখুন)
@interface NSMutableArray (QueueAdditions)
- (id)pop;
- (void)push:(id)obj;
@end
@implementation NSMutableArray (QueueAdditions)
- (id)pop
{
// nil if [self count] == 0
id lastObject = [[[self lastObject] retain] autorelease];
if (lastObject)
[self removeLastObject];
return lastObject;
}
- (void)push:(id)obj
{
[self addObject: obj];
}
@end
এখানে কোন আসল সারি সংগ্রহের ক্লাস নেই, তবে কার্যকরভাবে একই জিনিসটির জন্য এনএস মিউটেবলআরারি ব্যবহার করা যেতে পারে। আপনি চাইলে সুবিধার্থে পপ / পুশ পদ্ধতি যুক্ত করতে একটি বিভাগ নির্ধারণ করতে পারেন।
হ্যাঁ, NSMutableArray ব্যবহার করুন। এনএসমুটেবলআরে আসলে বাস্তবায়িত হয় 2-3 গাছ হিসাবে; স্বেচ্ছাসেবক সূচকগুলিতে NSMutableArray থেকে অবজেক্ট যোগ করার বা অপসারণের পারফরম্যান্স বৈশিষ্ট্যগুলির সাথে নিজেকে সাধারণত উদ্বেগের দরকার নেই।
যে বিভাগগুলিতে কোনও বিভাগ ব্যবহার করা হয় NSMutableArray
সেগুলি সত্যিকারের সারি নয়, কারণ NSMutableArray
ক্রিয়াকলাপগুলি উন্মুক্ত করে যেগুলি সারিগুলির একটি সুপারসেট। উদাহরণস্বরূপ, আপনাকে কিউয়ের মাঝামাঝি থেকে কোনও আইটেম সরানোর অনুমতি দেওয়া উচিত নয় (যেমন বিভাগগুলির সমাধানগুলি আপনাকে এখনও করতে দেয়)। অবজেক্ট ওরিয়েন্টেড ডিজাইনের একটি প্রধান নীতি, কার্যকারিতা সজ্জিত করা ভাল।
StdQueue.h
#import <Foundation/Foundation.h>
@interface StdQueue : NSObject
@property(nonatomic, readonly) BOOL empty;
@property(nonatomic, readonly) NSUInteger size;
@property(nonatomic, readonly) id front;
@property(nonatomic, readonly) id back;
- (void)enqueue:(id)object;
- (id)dequeue;
@end
StdQueue.m
#import "StdQueue.h"
@interface StdQueue ()
@property(nonatomic, strong) NSMutableArray* storage;
@end
@implementation StdQueue
#pragma mark NSObject
- (id)init
{
if (self = [super init]) {
_storage = [NSMutableArray array];
}
return self;
}
#pragma mark StdQueue
- (BOOL)empty
{
return self.storage.count == 0;
}
- (NSUInteger)size
{
return self.storage.count;
}
- (id)front
{
return self.storage.firstObject;
}
- (id)back
{
return self.storage.lastObject;
}
- (void)enqueue:(id)object
{
[self.storage addObject:object];
}
- (id)dequeue
{
id firstObject = nil;
if (!self.empty) {
firstObject = self.storage.firstObject;
[self.storage removeObjectAtIndex:0];
}
return firstObject;
}
@end
এটি আমার বাস্তবায়ন, আশা করি এটি সহায়তা করবে।
একধরনের সংক্ষিপ্তসার, সুতরাং আপনাকে অবশ্যই নতুন মাথাটি পপ এ সংরক্ষণ এবং পুরানো মাথাটি ত্যাগ করে মাথার ট্র্যাক রাখতে হবে
@interface Queue : NSObject {
id _data;
Queue *tail;
}
-(id) initWithData:(id) data;
-(id) getData;
-(Queue*) pop;
-(void) push:(id) data;
@end
#import "Queue.h"
@implementation Queue
-(id) initWithData:(id) data {
if (self=[super init]) {
_data = data;
[_data retain];
}
return self;
}
-(id) getData {
return _data;
}
-(Queue*) pop {
return tail;
}
-(void) push:(id) data{
if (tail) {
[tail push:data];
} else {
tail = [[Queue alloc]initWithData:data];
}
}
-(void) dealloc {
if (_data) {
[_data release];
}
[super release];
}
@end
আপনি কেবল এসটিএল সারিটি ব্যবহার করতে পারবেন না এমন কোনও বিশেষ কারণ রয়েছে? অবজেক্টিভ সি ++ হ'ল সি ++ এর একটি সুপারসেট (অবজেক্টিভ সি এর পরিবর্তে অবজেক্টিভ সি ++ ব্যবহার করার জন্য .m এর পরিবর্তে কেবলমাত্র মিমি ব্যবহার করুন)। তারপরে আপনি এসটিএল বা অন্য কোনও সি ++ কোড ব্যবহার করতে পারেন।
অবজেক্টিভ সি অবজেক্টের সাথে এসটিএল কিউ / ভেক্টর / লিস্ট ইত্যাদি ব্যবহার করার একটি বিষয় হ'ল তারা সাধারণত রক্ষণ / প্রকাশ / অটোরিলেজ মেমরি পরিচালনা সমর্থন করে না। এটি সহজেই সি ++ স্মার্ট পয়েন্টার ধারক শ্রেণীর সাথে কাজ করা হয় যা এটি নির্মাণের সময় তার উদ্দেশ্য সি অবজেক্টটি ধরে রাখে এবং ধ্বংস হয়ে গেলে মুক্তি দেয়। আপনি এসটিএল কিউতে কী রাখছেন তার উপর নির্ভর করে এটি প্রায়শই প্রয়োজন হয় না।
-count
ডিকুইউ করার মতো কোনও বস্তু আছে কিনা তা পরীক্ষা করতে আপনি আগেই কল করতে পারেন । সত্যিই এটি পছন্দ করার বিষয়।