【问题标题】:PHP foreach over an array of objectsPHP foreach 对象数组
【发布时间】:2010-03-05 05:38:03
【问题描述】:

我正在尝试对对象数组使用 foreach 循环。在 BeginBattle() 方法中,我想遍历所有对象并自动增加它们的播放次数。不幸的是,网络浏览器显示我有一个错误:致命错误:在 /nfs/c05/h01/mnt/70299/domains/munchkinparty.neededspace.net/ 中的非对象上调用成员函数 BattleInitiated() html/Battle.php 在第 75 行

有什么想法吗?

<?php
/* 
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

/**
 * Description of Battle
 *
 * @author joshualowry
 */
class Battle {
    /**
     *
     * @var <type>
     */
    private $_players;
    /**
     *
     * @var <type>
     */
    private $_battleInProgress;
    /**
     *
     */
    public function Battle(){
        $this->_players = array();
        $this->_battleInProgress = FALSE;

    }
    /**
     *
     * @param <type> $player
     * @return <type>
     */
    public function AddPlayer($player){
        if(!$this->_battleInProgress)
            $this->_players[] = $player;
        else
            return;
            //Spit some error
    }

    /**
     *
     * @param <type> $player
     * @return <type>
     */
    public function BattleWon($player){
        if($player != NULL)
            $player->BattleWon();
        else
            return;
            //Spit some error
    }
    /** GetPlayerByName Get the player's object by the player's name field.
     *
     * @param <type> $playerName
     * @return <type>
     */
    public function GetPlayerByName($playerName){
        foreach($this->_players as &$player) {
            if($player->GetName() == $playerName)
        return $player;
        }
        return NULL;
    }

    /**
     *
     */
    public function BeginBattle(){
        $this->_battleInProgress = TRUE;
        foreach($this->_players as $player){
        $player->BattleInitiated();
    }
    }
    /**
     *
     */
    public function DisplayCurrentBoard() {
        echo "Name  Alias   Wins    Battles<br/>";
        foreach($this->_players as &$player){
            echo "$player->GetName()    $player->GetAlias() $player->GetWins()  $player->GetBattles()<br/>";
        }
    }

}
?>

这是声明和调用所有内容的地方:

<?php
    include 'Battle.php';
    include 'Person.php';
    include 'Player.php';

    $currentBattle = new Battle();

    $playerA = new Player("JohnnyDanger","John",0,0);
    $playerB = new Player("JoshTheJest","Josh",0,0);
    $PlayerC = new Player("CarbQueen","Nicole",0,0);

    $currentBattle->AddPlayer($playerA);
    $currentBattle->AddPlayer($playerB);
    $currentBattle->AddPlayer($playerC);

    $currentBattle->BeginBattle();
    $currentBattle->BattleWon($currentBattle->GetPlayerByName("Josh"));
    $currentBattle->DisplayCurrentBoard();
?>

播放器类

    <?php

    /**
    * Description of Player
    *
    * @author joshualowry
    */
    class Player extends Person {

        private $_alias;
        private $_wins;
        private $_battles;

        public function Player($name, $alias, $wins, $battles) {
            parent::SetName($name);
            $this->_alias = $alias;
            $this->_battles = $battles;

            if($battles == 0) {
                $this->_wins = 0;
            }
            else {
                $this->_wins = $wins;
            }
        }

        protected function SetAlias($value){
            $this->_alias = $value;
        }

        public function GetAlias(){
            return $this->_alias;
        }

        protected function SetBattles($value) {
            $this->_battles = $value;
        }

        public function GetBattles(){
            return $this->_battles;
        }

        protected function SetWins($value) {
            $this->_wins = $value;
        }

        public function GetWins() {
            return $this->_wins;
        }

        public function BattleWon(){
            $this->_wins += 1;
        }

        public function BattleInitiated(){
            $this->_battles += 1;
        }

    }

?>

【问题讨论】:

  • 告诉我们在哪里调用 AddPlayer。
  • 你传递给 AddPlayer() 什么?
  • 您如何实例化您的Battle() 对象并调用AddPlayer()BeginBattle() 函数?
  • 你有一个 Player 类和一个合适的构造函数 [php.net/manual/en/language.oop5.decon.php] ?
  • @JannieT 您的链接给出了 404。

标签: php arrays foreach iteration


【解决方案1】:

错误消息表明您正在尝试对不是对象的东西使用所有BattleInitiated() 方法。

从你的代码来看,问题似乎出在这个循环上,在BeginBattle()方法中:

foreach($this->_players as $player){
    $player->BattleInitiated();
}

这意味着你的数组中至少有一个 $player 可能不是一个对象;也许是null,或者是一个数组?


要了解更多信息,您应该在循环之前使用var_dump 显示$this-&gt;_players 的内容,以确保它包含您期望的内容:

public function BeginBattle(){
    var_dump($this->_players);
    $this->_battleInProgress = TRUE;
    foreach($this->_players as $player){
        $player->BattleInitiated();
    }
}

如果$this-&gt;_players 不包含您所期望的(它可能不包含!),那么您必须找出原因...


考虑到$this-&gt;_playersAddPlayer() 方法修改,它将接收到的内容添加到数组的末尾,我敢打赌AddPlayer() 在没有正确$player 作为参数的情况下至少被调用一次。

为此,您可以在添加的$player 上使用var_dump

public function AddPlayer($player){
    var_dump($player);
    if(!$this->_battleInProgress)
        $this->_players[] = $player;
    else
        return;
        //Spit some error
}

如果var_dump 至少有一次表明$player 不是一个对象(例如,它是null,或者一个数组,或者一个字符串,...),那就是你的致命错误的原因。

【讨论】:

  • 我在上面添加了一些代码,但是第三个播放器 PlayerC 在使用 AddPlayer 添加后为空...有什么想法吗?
  • 我刚刚意识到我添加的是 $PlayerC 而不是 $playerC。您的回答帮助我找到了错误。当玩家被添加到战斗中时,我添加了一个检查,以查看它是否是“玩家”。现在不会添加 NULL vars 和其他类型。
  • 很高兴看到您找到了导致问题的原因 :-) 感谢您的解释 :-)
【解决方案2】:

你没看到吗??

都是因为一个小错字:

 $playerA = new Player("JohnnyDanger","John",0,0);
    $playerB = new Player("JoshTheJest","Josh",0,0);
    $PlayerC = new Player("CarbQueen","Nicole",0,0);

    $currentBattle->AddPlayer($playerA);
    $currentBattle->AddPlayer($playerB);
    $currentBattle->AddPlayer($playerC);

声明:$_P_layerC 使用:$_p_layerC

改正就可以了

【讨论】:

  • 感谢您回顾这一点。正如您将看到我对已接受答案的评论指出,发帖人的提示帮助我找到了错字,还帮助我意识到我需要在添加条目之前对其进行验证。
【解决方案3】:

您的 $player 变量是 null 或不是您想要的 typeObject

PlayerObject 是你的播放器类名。

例如

$battle=new Battle();
$player1=new PlayerObject();
$player2="player";
$battle->AddPlayer($player1);
$battle->AddPlayer($player2);
$battle->BeginBattle();

当您调用 BeginBattle() 时,$player1-&gt;BattleInitiated(); 将成功,但 $player2-&gt;BattleInitiated() 将给您致命错误并停止您的代码运行。如果$player2 为空、整数或不是PlayerObject 的东西,则相同。

【讨论】:

    猜你喜欢
    • 2012-11-22
    • 2021-04-14
    • 2012-11-02
    • 2016-06-20
    • 2023-03-10
    • 2021-01-19
    • 1970-01-01
    • 2014-03-20
    • 2012-06-21
    相关资源
    最近更新 更多