Objective-C状态机传入参数

时间:2011-10-25 10:48:08

标签: objective-c state-machine

我感兴趣地阅读了这篇文章给StackOverflow: How to Make a Basic Finite State Machine in Objective-C

我用这个作为基础,为简单的足球比赛建立我的状态机。我有状态防守,攻击,停止,中立。我创建了状态机,它将打印出NSLog“Now Entering State Defend”等。

现在我想将我的足球队的参考传递给状态机,以便我可以让我的团队根据状态做一些事情。即如果它是Defend,我可以让我的球员站在对手旁边。

我尝试了很多不同的方法,但都以语法错误结束。我很欣赏正确的方向推进

TeamState.h注意我在评论中的错误

@class TeamState;

#import <Foundation/Foundation.h>
#import "FootballTeam.h"

@protocol TeamStateProt 

-(void) enterTeamState:(TeamState*)team;
-(void) executeTeamState:(TeamState*)team;
-(void) exitTeamState:(TeamState*)team;

@end


@interface TeamState : NSObject{
    id<TeamStateProt> currentTeamState;

    id<TeamStateProt> Stoppage;
    id<TeamStateProt> Neutral;
    id<TeamStateProt> Defend;
    id<TeamStateProt> Attack;

    FootballTeam *footballTeam;  //ERROR Unknown Type name FootballTeam 
}

@property (nonatomic, retain) id<TeamStateProt> currentTeamState;
@property (nonatomic, retain) id<TeamStateProt> Stoppage;
@property (nonatomic, retain) id<TeamStateProt> Neutral;
@property (nonatomic, retain) id<TeamStateProt> Defend;
@property (nonatomic, retain) id<TeamStateProt> Attack;

- (id)initWithFootBallTeam:(FootballTeam*) team; //Error Expected a Type
-(void)update;
-(void)changeState:(id<TeamStateProt>) newState;
-(void)executeState:(id<TeamStateProt>) State;
@end

TeamState.m

#import "TeamState.h"
#import "FootballTeam.h"
#import "Stoppage_TS.h"
#import "Neutral_TS.h"
#import "Defend_TS.h"
#import "Attack_TS.h"


@implementation TeamState 

@synthesize currentTeamState;
@synthesize Stoppage, Neutral, Defend, Attack;

- (id)init
{
    self = [super init];
     if (self) {
        // Initialization code here.
        id<TeamStateProt>  s = [[Stoppage_TS alloc] init];
        self.Stoppage = s;

        id<TeamStateProt>  n = [[Neutral_TS alloc] init];
        self.Neutral = n;

        id<TeamStateProt>  d = [[Defend_TS alloc] init];
        self.Defend = d;

        id<TeamStateProt>  a = [[Attack_TS alloc] init];
        self.Attack = a;

        self.currentTeamState = n;
        [self.currentTeamState enterTeamState:self];
        [self executeState:self.currentTeamState];
    }

    return self;
}

- (id)initWithFootBallTeam:(FootballTeam*) team
{
    self = [super init];
    if (self) {
        // Initialization code here.
        id<TeamStateProt>  s = [[Stoppage_TS alloc] init];
        self.Stoppage = s;


        id<TeamStateProt>  n = [[Neutral_TS alloc] init];
        self.Neutral = n;

        id<TeamStateProt>  d = [[Defend_TS alloc] init];
        self.Defend = d;

        id<TeamStateProt>  a = [[Attack_TS alloc] init];
        self.Attack = a;

        self.currentTeamState = n;
        [self.currentTeamState enterTeamState:self];
        [self executeState:self.currentTeamState];

        footballTeam = team;
    }

    return self;
}

-(void)changeState:(id<TeamStateProt>) newState{
    NSLog(@"Changing State");
    if (newState != nil) {
        NSLog(@"Changing a state which isn't nil");
        [self.currentTeamState exitTeamState:self];
        self.currentTeamState = newState;
        [self.currentTeamState enterTeamState:self];
        [self executeState:self.currentTeamState];
    }

}

-(void)executeState:(id<TeamStateProt>) State{
    [self.currentTeamState executeTeamState:self];
}

// Each update, execute the execute state on the current team state
-(void)update{
    [self executeState:self.currentTeamState];
}
@end

FootballTeam.h

#import <Foundation/Foundation.h>
#import "Player.h"
#import "TeamState.h"
#import "Football.h"

typedef enum  {
    Home,
    Away
} TeamType;

@interface FootballTeam : NSObject{
    Player *ReceivingPlayer;    //Player to receive the ball
    Player *ClosestToBall;      //Player closest to the ball
    Player *ControllingPlayer;  //Player who has the ball can be NULL
    Player *SupportingPlayer;   //Player in a position to receive the ball

    NSMutableArray *players;    //Array of all the Players on this team

    TeamState *state;           //Current state of the teams state machine

    TeamType type;              //Defines if Home team or Away team
}

@property (nonatomic) TeamType type;
@property(nonatomic, retain) TeamState *state;

-(void) sendPlayersToHome;
-(Player*) playerClosestToBall:(Football*) ball;
-(BOOL) areAllPlayersAtHome;

@end

1 个答案:

答案 0 :(得分:1)

你有循环引用。您在FootballTeam.h中导入TeamState.h,反之亦然。

要避免这种情况,请仅导入.m文件中的.h文件,并在.h文件中添加前向声明。

所以,在TeamState.h中:

@class FootballTeam;

将导入移至TeamState.m

在FootballTeam中也是如此。