Неустранимая ошибка: использование $ this вне контекста объекта в Expense.php в строке 10

#php #oop

#php #ооп

Вопрос:

Я нашел здесь так много похожих вопросов, но я этого не понимаю, потому что я новичок в ООП.

Я следовал этой серии руководств, чтобы изучить ООП.

Вот мой код:

 include_once 'core/init.php';

if(Session::exists('home')){
    echo Session::flash('home');
}

$user = new User();
if($user->isLoggedIn()){
} else {
    Redirect::to('index.php');
}

if(Input::exist()){
    $validate = new Validate();
    $validation = $validate->check($_POST, array(
        'date' => array('required' => true),
        'vendor' => array('required' => true),
        'invoice-no' => array('required' => true),
        'terms-or-payment-account' => array('required' => true),
        'type-of-expense-1' => array('required' => true),
        'description-1' => array('required' => true),
        'quantity-1' => array('required' => true),
        'price-1' => array('required' => true),
        'amount-1' => array('required' => true)
    ));

    if($validation->passed()){
        $expense = new Expense();
        try{
            $expense->record(array(
                'date' => Input::get('date'),
                'vendor' => Input::get('vendor'),
                'invoice-no' => Input::get('invoice-no'),
                'terms-or-payment-account' => Input::get('terms-or-payment-account'),
                'type-of-expense' => Input::get('type-of-expense-1'),
                'description' => Input::get('description-1'), 
                'quantity' => Input::get('quantity-1'),
                'price' => Input::get('price-1'),
                'amount' => Input::get('amount-1')
            ));
        } catch(Exception $e){
            die($e->getMessage());
        }
        if($expense->record()){
            echo 'success';
        }
    } else {
         //output errors
        foreach ($validation->errors() as $error) {
            echo $error, '<br/>';
        }
    }
}
  

Expense.php:

 class Expense{
    private $_db;

    public function __construct($expense = NULL){
        $this->_db = DB::getInstance();
    }

    public static function record($fields){
        if(!$this->_db->insert('expenses', $fields)){
            throw new Exception('There is a problem recording expense');
        }
    }
}
  

пожалуйста, помогите мне решить эту проблему. Спасибо

Комментарии:

1. У нас нет номеров строк в SO. Redirect::to('index.php'); Ваша строка 10? Если это так, отредактируйте свой вопрос и добавьте комментарий в свою строку типа // here is line 10 - where it fails .

2. это было if (!$this->_db-> insert(‘расходы’, $ поля)){ и у меня есть класс перенаправления, который вы упомянули.

3. теперь мой файл класса расходов выглядит следующим образом. расходы класса { запись общедоступной функции ($fields){ if(DB::getInstance()->insert(‘расходы’, $ fields)){ создать новое исключение (‘Существует проблема с записью расходов’); } }}

Ответ №1:

Expense#record Функция статична. Это означает, что экземпляр объекта еще не создан, но класс создан. $this является указателем на созданный объект. Поскольку в области действия этого метода нет созданного объекта, $this всегда будет возвращать значение null. Ошибка, которую вы видите, — это способ PHP сообщить вам об этом.

Самый простой способ заставить это работать — удалить static из Expense#record подписи метода. Это сделало бы метод методом объекта Expense вместо метода класса Expense, как сейчас. Поскольку вы уже создаете экземпляр объекта затрат после $validation->passed() , это не должно быть проблемой. ->record() Метод будет работать так, как ожидалось.

Если вы абсолютно хотите сохранить метод записи как static , то вам придется изменить метод для работы в статическом контексте; как показано ниже

 class Expense{
    private static $_db = DB::getInstance();

    public static function record($fields){
        if(!self->_db->insert('expenses', $fields)){
            throw new Exception('There is a problem recording expense');
        }
    }
}
  

Комментарии:

1. @YaskyThanks, спасибо всем

Ответ №2:

Переменная ‘this‘ — это просто ссылка на объект, который вызвал метод. Но вы используете статический модификатор. Это означает, что этот метод используется во всем классе, а не в каком-либо объекте. Также это означает, что не существует объекта, который вызывает этот метод, и, очевидно, не существует переменной ‘this‘.

В статическом методе вы можете использовать только переменную ‘self‘. Это ссылка на класс self.

И для устранения вашей ошибки вам необходимо удалить статический модификатор.

Комментарии:

1. ПРИВЕТ, спасибо за ваш ответ. я только что дублировал пользовательский класс.

2. вы имеете в виду вот так? общедоступная запись статической функции ($fields){ DB::getInstance()->insert(‘расходы’, $ fields)){ создать новое исключение (‘Существует проблема с записью расходов’); } }

3. когда я изменил на эту запись общедоступной статической функции ($fields){ DB::getInstance()-> insert(‘расходы’, $ fields); } отправленная запись,

4. Не совсем, но это тоже возможно. Если вы будете использовать DB::getInstance(), то вы можете удалить ‘construct’, потому что в этом нет необходимости. И я предложил удалить ‘static’ модификатор из метода public function record($fields) . Поскольку вы получаете экземпляр db в конструкторе, другие методы этого класса могут работать с этим подключением.

5. Спасибо за ваши ответы. <pre><code> Предупреждение: Отсутствует аргумент 1 для Expense::record(), вызываемый в expense.php в строке 45 и определено в Expense.php в строке 4 Предупреждение NULL: array_keys() ожидает, что параметр 1 будет массивом, значение null указано в DB.php в строке 76 Предупреждение: недопустимый аргумент, предоставленный для foreach() в DB.php в строке 80 предупреждение: implode(): недопустимые аргументы, переданные в DB.php в строке 88