我有2个文件。 一个是index.php,它检查用户登录 在这个文件中,我创建了一个处理数据库的dbManager类。 如果dbManager可以验证登录数据,我将用户转发到lobby.php(通过标题)。
在lobby.php中,我创建了一个管理大厅的Manager类。 我希望能够使用Manager类将查询转发到DB Manager,如下所示:
的index.php
$dbManager = new dbManager();
$userid = $dbManager->validateLogin(($_POST["name"], $_POST["pass"];
if ($userid){
$_SESSION["userid"] = $userid;
header("Location: lobby.php");
}
lobby.php
session_start();
if (isset($_SESSION["userid"])){
$manager = new Manager($_SESSION["userid"]);
$manager->getGames();
}
Class dbManager {
things
}
Class Manager {
public userid;
function __construct($id){
$this->userid = $id;
}
function getGames(){
$ret = $dbManager->queryDB($this->userid);
}
}
我收到以下通知:
注意:未定义的变量:第11行的D:\ SecureWAMP_Portable \ htdocs \ projectX \ gameManager.php中的dbManager
和
致命错误:在第11行的D:\ SecureWAMP_Portable \ htdocs \ projectX \ gameManager.php中的非对象上调用成员函数getGamesForPlayer()
我做错了什么?
答案 0 :(得分:1)
你不应该使用全球变量因为它是糟糕的风格,并且当应用程序变大时会让你的生活变得非常困难。
在您的情况下,您希望在不同的类中使用dbManager。 由于可能经常使用db事务,因此请查看单例模式,因此该类只能有一个实例。
但请注意,你应该保持单身人数尽可能低。
查看此页面以了解如何在PHP中实现单例模式: http://www.phptherightway.com/pages/Design-Patterns.html
答案 1 :(得分:1)
您似乎对如何在多个文件中分发和使用php代码以及如何使用这些文件存在误解。
例如,如果您使用include()
或require()
代替header()
,则可以参考目前为止定义的数据。
更高级的方法是使用__autoload()
或[spl_autoload_register()](http://php.net/manual/de/function.spl-autoload-register.php)
将类加载到脚本中,并使用index.php
启动脚本。
(另请阅读@ blacksheep_2011提供的链接)
答案 2 :(得分:1)
一个好的做法是将每个类声明在单独的文件中。
之后,您需要将所需的类包含在您计划使用该类功能的文件中。
创建文件 DBManager.php :
Class DBManager {
things
}
创建文件 Manager.php ,其中包含Manager
类声明:
include('DBManager.php');
Class Manager {
public userid;
function __construct($id){
$this->userid = $id;
}
function getGames(){
$dbManager = new DBManager();
$ret = $dbManager->queryDB($this->userid);
}
}
将课程包括在需要的地方:
的的index.php 强>
require_once 'DBManager.php';
$dbManager = new DBManager();
$userid = $dbManager->validateLogin(($_POST["name"], $_POST["pass"];
if ($userid){
$_SESSION["userid"] = $userid;
header("Location: lobby.php");
}
<强> lobby.php 强>
session_start();
require_once 'Manager.php';
if (isset($_SESSION["userid"])){
$manager = new Manager($_SESSION["userid"]);
$manager->getGames();
}
答案 3 :(得分:1)
您应该在新文件中定义每个类并包含这些文件(良好做法是使用自动加载)。如果您只需要一个类的一个对象,那么您应该看看Singleton模式,因为您将始终获得相同的类实例。
为此,您定义了一个静态保护变量,该变量将保存我们的类实例并使用静态公共方法返回类实例,并在必要时创建一个新类实例。我们将每个类的构造函数定义为private,因此必须使用静态公共方法。
如果你有参数传递给构造函数,也可以为静态公共方法定义它们,并将参数传递给静态公共方法中的构造函数。
文件DBManager.php将定义类DBManager并将使用单例模式,因为此类将处理与数据库的连接。
Class DBManager {
static protected $instance = NULL
private __construct() {
//Write the code you want to execute when a new class instance is requested
self::$instance = &$this; //Put a reference to this instance in our static variable
}
//Our static public method to retrieve a class instance
static public app() {
if(self::$instance === NULL OR !is_a(self::$instance, 'DBManager')) { //With is_a we are making sure our self::$instance variable holds a class instance of DBManager
$instance = new DBManager();
}
return self::$instance;
}
/* All your other methods... */
}
我们的Manager.php将保存类管理器并检索DBManager的类实例,我们将调用静态公共方法 app()。它也可以使类Manager成为单例,但前提是只存在一个类实例。
Class Manager {
public userid;
function __construct($id){
$this->userid = $id;
}
function getGames() {
$ret = DBManager::app()->queryDB($this->userid);
}
}
现在我们的基本index.php而不是使用new DBManager()
,我们将使用静态方法返回一个类实例。
require_once 'DBManager.php';
$dbManager = DBManager::app();
$userid = $dbManager->validateLogin($_POST['name'], $_POST['pass']);
if($userid) {
$_SESSION['userid'] = $userid;
header("Location: lobby.php");
}
在我们的lobby.php中,我们将首次使用新的Manager类。
session_start();
require_once 'DBManager.php';
require_once 'Manager.php';
$dbManager = DBManager::app();
if(isset($_SESSION['userid'])) {
$manager = new Manager($_SESSION['userid']);
$manager->getGames();
}