我正在构建我的第一个PHP应用程序。我想从csv文件中读取公共汽车时间,然后向ti用户提供从他们的住所到我们大学的下一班车。这是我第一次使用PHP,所以要温柔:
<?php
// configuration
require("../includes/config.php");
if (!empty($_SESSION["id"]))
{
//lookup database entries for house
$users = query("SELECT * FROM users WHERE id = ?", $_SESSION["id"]);
if ($users === false)
{
apologize("Sorry, there was an error");
}
//lookup database entries for house
$residences = query("SELECT * FROM residences WHERE id = ?", $users[0]["residence"]);
if ($residences === false)
{
apologize("Sorry, there was an error");
}
//if user specified a residence in his profile
if($residences[0]["id"] != 0)
{
$times = array();
//if there is no bus today, in this case sat and sun
if(date( "w", $timestamp) == 0 || date( "w", $timestamp) == 6)
{
$times[0] = "There is no bus today";
}
//load the busplan for his residence
else
{
//open file and load in array if time is higher than date("His");
$timesList = file_get_contents($users[0]["residence"] . ".csv");
$nextbuses = explode(',', $timesList);
$hoursMins = date("Gi");
$num = 0;
for($i = 0; $i < count($nextbuses); $i++)
{
if($hoursMins < $nextbuses[$i])
{
$times[$num] = $nextbuses[$i];
$num++;
}
}
}
render("shuttle_show.php", ["title" => "Next Shuttle from your residence.", "times" => $times]);
}
}
这使用函数查询:
function query(/* $sql [, ... ] */)
{
// SQL statement
$sql = func_get_arg(0);
// parameters, if any
$parameters = array_slice(func_get_args(), 1);
// try to connect to database
static $handle;
if (!isset($handle))
{
try
{
// connect to database
$handle = new PDO("mysql:dbname=" . DATABASE . ";host=" . SERVER, USERNAME, PASSWORD);
// ensure that PDO::prepare returns false when passed invalid SQL
$handle->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
}
catch (Exception $e)
{
// trigger (big, orange) error
trigger_error($e->getMessage(), E_USER_ERROR);
exit;
}
}
// prepare SQL statement
$statement = $handle->prepare($sql);
if ($statement === false)
{
// trigger (big, orange) error
trigger_error($handle->errorInfo()[2], E_USER_ERROR);
exit;
}
// execute SQL statement
$results = $statement->execute($parameters);
// return result set's rows, if any
if ($results !== false)
{
return $statement->fetchAll(PDO::FETCH_ASSOC);
}
else
{
return false;
}
}
它使用的其他功能与我猜不相关。现在我似乎无法找到为什么会继续产生:
注意:未定义的偏移量:第16行的/Applications/MAMP/htdocs/html/shuttle.php中为0
注意:未定义的偏移量:第22行/Applications/MAMP/htdocs/html/shuttle.php中的0
相关的行是
$residences = query("SELECT * FROM residences WHERE id = ?", $users[0]["residence"]);
和
if($residences[0]["id"] != 0)
会感激一些帮助! :)
编辑:
我将同一个文件传输到我的linux系统,没有任何更改,我得到了一个vardump。如果我在Mac上的MAMP上使用相同的vardump,则阵列为空。现在我得到:
var_dump($users);
array (size=1)
0 =>
array (size=5)
'id' => int 12
'username' => string 'frechdaxx' (length=9)
'mail' => string '*************@gmail.com' (length=23)
'hash' => string '$1$qr5axj4C$BET5zZGJza2DcHI8eD8fV0' (length=34)
'residence' => int 9573
为什么这是一个问题?在我访问用户表之前,函数查询使用完全相同的语法,因为我们可以看到它正确地返回所有其他值。
为什么我的环境有差异?我的MAMP服务器上的数组是空的,但适用于Linux。但是,查询功能的其他代码示例在两种环境下都能完美地运行
答案 0 :(得分:2)
这只是$users[0]["residence"]
不存在(未设置)。您应该在尝试使用它之前检查它。如您所见,这只是一个通知,而不是错误。这意味着在某些情况下,变量可以不设置,PHP不会抱怨太多,但这绝对不是一般规则。
我会将其更改为:
$users = query("SELECT * FROM users WHERE id = ?", $_SESSION["id"]);
if (empty($users[0]["residence"]))
{
apologize("Sorry, there was an error");
}
此外,这只是“修复”它。如果你想找到问题的根,那就是$users = query("SELECT * FROM users WHERE id = ?", $_SESSION["id"]);
中调用的query()函数:
// execute SQL statement
$results = $statement->execute($parameters);
// return result set's rows, if any
if ($results !== false)
{
$fetched = $statement->fetchAll(PDO::FETCH_ASSOC);
// Check that ther was actually something fetched
if(!empty($fetched))
{
return $fetched;
}
}
/* You don't need to return false, null is the default returned value.
* If you *want* it, then delete the else. */
}
从documentation开始,如果没有任何内容,fetchall将返回一个空数组,因此该函数可能会返回一个空数组。
答案 1 :(得分:1)
$users = query("SELECT * FROM users WHERE id = ?", $_SESSION["id"]);
if ($users === false) { }
您正在严格检查查询是否返回false,仅在查询或参数出错时才会发生。这不会检查是否返回了任何结果,并且您指的是不存在的第一个返回记录($users[0]["residence"]
)($users
是一个空数组)。
由于用户ID来自$_SESSION["id"]
,因此它应该存在并且在数据库中可用,但是您的代码中的某个地方可能会用其他ID覆盖它。