为了给你一些背景知识,流程是:连接到第三方API,将数据存储为json,转换为php并使用下面代码中的数据。
我最初找到this work但无法弄清楚如何根据我的需要修改它。也许你们其中一个人能更好地理解它?
我在这做三件事。首先检查房屋的ID + last_update标记,以确定需要在我的数据库中更新哪些房屋。如果它们存在但细节已更改,请删除当前数据并将其存储在准备插入的变量中。如果数据不存在,请插入。
需要注意的事项:脚本执行时间太长,我必须设置set_time_limit(0);我意识到这是不好的做法,但我需要强制完成脚本。
我已经将我的代码减少了很多,因为我有超过40种不同的手动输入准备语句:
我已经使用屏幕截图确定了预期的输出,所以请忽略任何开放的括号,因为主要问题是将代码改进为更动态的方法并使其更快。
<?php
$update = '';
$add = '';
if (!empty($houses)) {
foreach($houses as $travel_Prop) {
$Prop = $travel_Prop['data'][0]; // Need to check this!
if ($Prop['id'] > '0') { // Ignore empty arrays
$sql= "SELECT * FROM travel_a_property WHERE travel_prop_id = :travel_prop_id";
$stmt = $extDb->prepare("$sql");
$stmt->bindParam(':travel_prop_id', $Prop['id'], PDO::PARAM_INT);
$stmt->execute();
$Result = $stmt->fetchAll(PDO::FETCH_ASSOC);
if (!empty($Result)) {
$travel_last_update = $Prop['last_update'];
$local_last_update = $Result[0]['last_update'];
if ($travel_last_update > $local_last_update) {
$update[] = $Prop;
echo 'Property ID: ' .$Prop['id'] .' Property modified: Updating Records.<br>';
} else {
echo 'Property ID: ' .$Prop['id'] .' Property details: Up to Date.<br>';
}
} else {
$add[] = $Prop;
echo 'Property ID: ' .$Prop['id'] .' Property Created: Adding to Records.';
}
}
}
注意:代码将在屏幕截图输出后继续
# UPDATE
if (!empty($update)) {
//print_r($update);
foreach ($update as $PropUpdate) {
// Get all_prop_id
$sql= "SELECT * FROM travel_a_property WHERE travel_prop_id = :travel_prop_id";
$stmt = $extDb->prepare("$sql");
$stmt->bindParam(':travel_prop_id', $PropUpdate['id'], PDO::PARAM_INT);
$stmt->execute();
//$Result = $stmt->fetchAll(PDO::FETCH_ASSOC);
$obj = $stmt->fetchObject();
//echo $obj->filmName;
$all_prop_id = $obj->all_prop_id;
echo $all_prop_id;
// Update master db table a_property
$sql = "UPDATE travel_a_property SET last_update = :last_update
HERE all_prop_id = :all_prop_id";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':last_update', $PropUpdate['last_update'], PDO::PARAM_STR);
$stmt->bindParam(':all_prop_id', $all_prop_id, PDO::PARAM_INT);
$stmt->execute();
echo '<br>Prop Updated - all_prop_id : ' .$all_prop_id .'<br>';
# DELETe & INSERT
$sql = "DELETE FROM ot_b_address WHERE glob_prop_id = :glob_prop_id";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':glob_prop_id', $glob_prop_id, PDO::PARAM_INT);
$stmt->execute();
$sql = "INSERT INTO ot_b_address(glob_prop_id, address1, address2, city, state, zip_code,
country, latitude, longitude) VALUES ( :glob_prop_id, :address1, :address2, :city, :state,
:zip_code, :country, :latitude, :longitude)";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':glob_prop_id', $glob_prop_id, PDO::PARAM_INT);
$stmt->bindParam(':address1', $PropUpdate['address']['address1'], PDO::PARAM_STR);
$stmt->bindParam(':address2', $PropUpdate['address']['address2'], PDO::PARAM_STR);
$stmt->bindParam(':city', $PropUpdate['address']['city'], PDO::PARAM_STR);
$stmt->bindParam(':state', $PropUpdate['address']['state'], PDO::PARAM_STR);
$stmt->bindParam(':zip_code', $PropUpdate['address']['zip_code'], PDO::PARAM_STR);
$stmt->bindParam(':country', $PropUpdate['address']['country'], PDO::PARAM_STR);
$stmt->bindParam(':city', $PropUpdate['address']['city'], PDO::PARAM_STR);
// use PARAM_STR although a number
$stmt->bindParam(':latitude', $PropUpdate['address']['latitude'], PDO::PARAM_STR);
$stmt->bindParam(':longitude', $PropUpdate['address']['longitude'], PDO::PARAM_STR);
$stmt->execute();
echo 'Address Updated <br>';
$sql = "DELETE FROM travel_d_urls WHERE all_prop_id = :all_prop_id";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':all_prop_id', $all_prop_id, PDO::PARAM_INT);
$stmt->execute();
if (!empty($PropUpdate['urls'])) {
foreach($PropUpdate['urls'] as $row => $Url) {
$sql = "INSERT INTO travel_d_urls(all_prop_id, type, url)
VALUES ( :all_prop_id, :type, :url)";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':all_prop_id', $all_prop_id, PDO::PARAM_INT);
$stmt->bindParam(':type', $Url['type'], PDO::PARAM_STR);
$stmt->bindParam(':url', $Url['url'], PDO::PARAM_STR);
$stmt->execute();
echo 'URL '.$row .' Updated <br>';
}
}
}
} else {
echo 'no rates to Update <br>';
}
输出几乎是一样的(无论是什么更新) URL已添加 URL已添加 等
以下代码是最后一个if语句,它告诉脚本添加剩余的属性(如果它们不存在)。
} //结束foreach $ update
# INSERT ONLY
if (!empty($add)) {
foreach ($add as $PropAdd) {
$sql = "INSERT INTO travel_a_property(travel_prop_id, last_update)
VALUES ( :travel_prop_id, :last_update)";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':travel_prop_id', $PropAdd['id'], PDO::PARAM_INT);
$stmt->bindParam(':last_update', $PropAdd['last_update'], PDO::PARAM_STR);
$stmt->execute();
$all_prop_id = $extDb->lastInsertId(); // Use this ID in all the following record inserts
echo '<br>Prop Added - all_prop_id : ' .$all_prop_id .'<br>';
##########################
$sql = "INSERT INTO travel_b_address(all_prop_id, address1, address2, city, state, zip_code, country,
latitude, longitude) VALUES ( :all_prop_id, :address1, :address2, :city, :state, :zip_code, :country,
:latitude, :longitude)";
$stmt = $extDb->prepare($sql);
$stmt->bindParam(':all_prop_id', $all_prop_id, PDO::PARAM_INT);
$stmt->bindParam(':address1', $PropAdd['address']['address1'], PDO::PARAM_STR);
$stmt->bindParam(':address2', $PropAdd['address']['address2'], PDO::PARAM_STR);
$stmt->bindParam(':city', $PropAdd['address']['city'], PDO::PARAM_STR);
$stmt->bindParam(':state', $PropAdd['address']['state'], PDO::PARAM_STR);
$stmt->bindParam(':zip_code', $PropAdd['address']['zip_code'], PDO::PARAM_STR);
$stmt->bindParam(':country', $PropAdd['address']['country'], PDO::PARAM_STR);
// use PARAM_STR although a number
$stmt->bindParam(':latitude', $PropAdd['address']['latitude'], PDO::PARAM_STR);
$stmt->bindParam(':longitude', $PropAdd['address']['longitude'], PDO::PARAM_STR);
$stmt->execute();
echo 'Address Added <br>';
} // end foreach
} // end !empty
$extDb = null;
}
?>
所以重申一下,这里的问题不是要确定我的代码有什么问题而不是速度,它实际上工作正常。我想知道是否有人可以找出使这种动态更好的最佳方法,以避免繁琐地编写40多次代码?
如果有任何不清楚的地方,请告诉我。
干杯, 台上。
答案 0 :(得分:1)
您正在foreach循环中创建预准备语句。尝试在其外部创建预准备语句。准备好的语句的想法是,您准备一次语句并使用不同的参数值多次执行。这样,数据库只需编译和优化一次SQL查询,这比在迭代过程中更有效。
if (!empty($houses)) {
$stmt = $extDb->prepare("SELECT * FROM travel_a_property WHERE travel_prop_id = :travel_prop_id");
//$stmt2 = ...
foreach ($houses as $travel_Prop) {
$prop = $travel_Prop['data'][0]; // Need to check this!
if ($prop['id'] > '0') { // Ignore empty arrays
if ($stmt->execute(array(':travel_prop_id' => $prop['id']))) {
$result = $stmt->fetchAll(PDO::FETCH_ASSOC);
//Do something with $result
}
}
//$stmt2->execute(...);
}
}