Сравнить свойства 2 экземпляров из метода внешнего класса — необходимо для карточной игры iPhone

#iphone #objective-c #cocoa #cocoa-touch #ios

#iPhone #objective-c #cocoa #cocoa-touch #iOS

Вопрос:

Я внедряю карточную игру для iphone. В моем классе модели каждая карта имеет N атрибутов.

 @interface Card : NSObject {

    NSInteger attribute1;
    NSInteger attribute2;
        ....................;

    NSInteger attributeN;
}
  

Я хочу создать класс контроллера, который сравнивает 2 карты для атрибута, который пользователь выбирает из интерфейса. Проблема в том, что я не знаю, как ссылаться на атрибуты внешней карты с помощью класса контроллера.

например. Когда пользователь нажимает на атрибут, я хочу, чтобы подобный метод вызывался в классе контроллера.

 - (Player) winnerOfComparisonBetween:(Card *) card1 andCard:(Card *) card2 forAttribute:??? {
    if (card1.selectedAttribute** < card2.selectedAttribute)
         return card1.owner

     ....
     ....
}
  

Есть идеи о том, как реализовать этот метод, и что поставить вместо вопросительных знаков? Любая помощь была бы действительно оценена.

Ответ №1:

Взгляните на performSelector NSObject и NSSelectorFromString.

Попробуйте что-то вроде этого :

 - (Player)winnerOfComparisonBetween:(Card *)card1 andCard:(Card *)card2 forAttribute:(NSString *)attributeName {

    SEL selector = NSSelectorFromString(attributeName);
    id a = [card1 performSelector:selector];   
    id b = [card2 performSelector:selector];

    NSComparisonResult result = [a compare:b];

    if (NSOrderedAscending == result)
        return card1.owner;
    else if (NSOrderedDescending == result)
        return card2.owner;
    else
        NSLog(@"They're the same");
}
  

Хотя в этом коде предполагается, что все атрибуты реализуют метод compare: . (NSStrings уже это делают, так что вы, вероятно, в порядке)

Если также предполагается, что все атрибуты являются объектами, т. Е. у вас не может быть чисел с плавающей точкой или целых чисел, у вас должны быть NSNumbers.

И нет проверки ошибок, чтобы сделать его более читаемым — вам нужно убедиться, что attributeName было допустимым именем для атрибута, иначе это может привести к сбою — взгляните на responsestoselector: чтобы проверить, могут ли ваши объекты card выполнять селектор 🙂

Ответ №2:

Используйте этот, если у вас все еще есть проблемы с этим, дайте мне знать … 🙂

 - (Player) winnerOfComparisonBetween:(Card *) card1 andCard:(Card *) card2 forAttribute:(NSInteger)attribute {


    switch (attribute) {
        case attribute1:
            if (card1.attribute1 < card2.attribute1)
                return card1.owner
                }
            break;


        case attribute2:
            if (card1.attribute2 < card2.attribute2)
                return card1.owner
                }
            break;


        .
        .
        .
        .
        .

        case attributeN:
            if (card1.attributeN < card2.attributeN)
                    return card1.owner
                }
            break;


        default:
            break;
}