[英]Convert C# generic method to objective-C
我的一位同事向我求了一点帮助。 我是一名C#开发人员,他是一名iOS开发人员,每次阅读代码都会给我们一些很好的见解。
他正在编写一些需要返回基类UITableViewCell
对象的函数,并且有一个整数作为输入。 实际的返回类型是UITableViewCell
的子类。 他问我是否知道一个更好的解决方案然后是一个简单的开关:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
switch (row) {
case 0: {
NSString *CellIdentifier = @"personCell";
PersonInfoCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[PersonInfoCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
break;
}
case 1: {
NSString *CellIdentifier = @"photoCell";
PhotoCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[PhotoCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
break;
}
default:
return nil; //Don't care about this atm. Not the problem.
break;
}
}
我的C#实现将如下所示:
public UITableViewCell TableViewCellForRowAtIndexPath(UITableView tableView, NSIndexPath indexPath)
{
switch(indexPath.row)
{
case 0:
return MakeCell<PersonInfoCell>();
case 1:
return MakeCell<PhotoCell>();
default:
return null; //Still doesn't matter
}
}
public TCell MakeCell<TCell>() where TCell : UITableViewCell, new()
{
TCell cell = new TCell();
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
}
public class PersonInfoCell : UITableViewCell
{
//Dont care about implementation yet....
//TL;DR
}
public class PhotoCell : UITableViewCell
{
//Dont care about implementation yet....
//TL;DR
}
有谁知道将我的C#通用代码转换为objective-c equilivant的方法?
我们错误的实施基于尼古拉斯凯里的想法。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
switch (row) {
case 0: {
NSString *CellIdentifier = @"personCell";
PersonInfoCell *cell = (PersonInfoCell *)[self makeCell:CellIdentifier];
//Do PersonInfoCell specific stuff with cell
return cell;
break;
}
case 1: {
NSString *CellIdentifier = @"photoCell";
PhotoCell *cell = (PhotoCell *)[self makeCell:CellIdentifier];
//Do PhotoCell specific stuff with cell
return cell;
break;
}
default:
return nil; //Don't care about this atm. Not the problem.
break;
}
}
- (id *)makeCell:(NSString *)cellIdentifier
{
id cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil) {
cell = [[PhotoCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier]; // <---- how does this method know it is a PhotoCell I want?
//PhotoCell???
}
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
}
在Objective-C中,类是第一类构造,可以像任何其他对象一样传递和使用。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *cellIdentifier = nil;
Class cellClass = nil;
switch (row) {
case 0:
cellIdentifier = @"personCell";
cellClass = [PersonInfoCell class];
break;
case 1:
cellIdentifier = @"photoCell";
cellClass = [PhotoCell class];
break;
default:
return nil; //Don't care about this atm. Not the problem.
}
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil)
cell = [[cellClass alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
}
如果你真的想要分解出厂方法,你可以这样做:
- (UITableViewCell *)getOrCreateCellForTable:(UITableView *)tableView withIdentifier:(NSString *)cellIdentifier class:(Class)cellClass
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil)
cell = [[cellClass alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
}
如果要删除配对的cellIdentifier
和cellClass
参数,可以选择在您使用的每个单元类上创建一个defaultIdentifier
类方法( static
方法,在C#范围内)。 这样,您可以只将类传递给工厂方法,并且工厂方法可以在类中查询正确的标识符。
基于David Mitchell的代码,我们(Synercoder的同事)提出了这个,完美的工作!
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *cellIdentifier = nil;
Class cellClass = nil;
switch (indexPath.row) {
case 0: {
cellIdentifier = @"personCell";
cellClass = [PersonInfoCell class];
PersonInfoCell *personInfoCell = (PersonInfoCell *)[self getOrCreateCellForTable:tableView withIdentifier:cellIdentifier class:cellClass];
personInfoCell.delegate = self;
return personInfoCell;
}
case 1: {
cellIdentifier = @"photoCell";
cellClass = [LastMeasureMent class];
LastMeasureMent *measurementCell = (LastMeasureMent *)[self getOrCreateCellForTable:tableView withIdentifier:cellIdentifier class:cellClass];
measurementCell.selectionStyle = UITableViewCellSelectionStyleBlue;
return measurementCell;
}
default: {
cellIdentifier = @"photoCell";
cellClass = [LastMeasureMent class];
LastMeasureMent *measurementCell = (LastMeasureMent *)[self getOrCreateCellForTable:tableView withIdentifier:cellIdentifier class:cellClass];
measurementCell.selectionStyle = UITableViewCellSelectionStyleBlue;
return measurementCell;
}
}
}
- (UITableViewCell *)getOrCreateCellForTable:(UITableView *)tableView withIdentifier:(NSString *)cellIdentifier class:(Class)cellClass
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil)
cell = [[cellClass alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
return cell;
}
谢谢大卫!
看到这个问题: Objective-C中是否有强类型集合?
Objective-C是后期绑定和动态类型,因此您不需要泛型。 您可以将任何消息发送到对象。 它用它做什么取决于对象。 具有静态类型的早期语言(如C#,Java,C ++)需要泛型。 没有它们,问题就不会[很容易]知道它对所包含的对象能做什么或不能做什么。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.