Vâng, đó là thực hành tốt để sử dụng mysql_free_result($result)
. Tài liệu được trích dẫn trong câu trả lời được chấp nhận là không chính xác. Đó là những gì tài liệu nói, nhưng điều đó không có ý nghĩa gì cả. Dưới đây là những gì nó says:
mysql_free_result() chỉ cần được gọi nếu bạn lo ngại về số lượng bộ nhớ đang được sử dụng cho các truy vấn trả lại tập kết quả lớn. Tất cả bộ nhớ kết quả được liên kết sẽ tự động được giải phóng ở cuối quá trình thực thi của tập lệnh.
Phần đầu tiên của câu đầu tiên là chính xác. Đúng là bạn không cần sử dụng nó vì những lý do khác với những lo ngại về bộ nhớ. Lo ngại về bộ nhớ là lý do duy nhất để sử dụng nó. Tuy nhiên, phần thứ hai của câu đầu tiên không có ý nghĩa gì cả. Yêu cầu bồi thường là bạn sẽ chỉ quan tâm đến bộ nhớ cho các truy vấn trả lại các tập kết quả lớn. Điều này là rất gây hiểu nhầm vì có những trường hợp phổ biến khác mà bộ nhớ là một mối quan tâm và gọi mysql_free_result()
là thực hành rất tốt. Mọi truy vấn thời gian có thể chạy một số lần không xác định, càng nhiều bộ nhớ sẽ được sử dụng hết nếu bạn không gọi mysql_free_result()
. Vì vậy, nếu bạn chạy truy vấn của bạn trong một vòng lặp, hoặc từ một chức năng hoặc phương pháp, nó thường là một ý tưởng tốt để gọi mysql_free_result()
. Bạn chỉ cần cẩn thận để không giải phóng kết quả cho đến khi nó không còn được sử dụng nữa.Bạn có thể tự bảo vệ mình khỏi phải suy nghĩ về thời gian và cách sử dụng nó bằng cách tạo các hàm select() và ex() của riêng bạn để bạn không làm việc trực tiếp với các tập kết quả. (Không có mã nào ở đây chính xác là cách tôi thực sự viết nó, nó minh họa hơn. Bạn có thể muốn đặt chúng trong một lớp hoặc vùng tên đặc biệt và ném một loại Ngoại lệ khác hoặc tham số bổ sung như $class_name
, v.v. .)
// call this for select queries that do not modify anything
function select($sql) {
$array= array();
$rs= query($sql);
while($o= mysql_fetch_object($rs))
$array[]= $o;
mysql_free_result($rs);
return $array;
}
// call this for queries that modify data
function ex($sql) {
query($sql);
return mysql_affected_rows();
}
function query($sql) {
$rs= mysql_query($sql);
if($rs === false) {
throw new Exception("MySQL query error - SQL: \"$sql\" - Error Number: "
.mysql_errno()." - Error Message: ".mysql_error());
}
return $rs;
}
Bây giờ nếu bạn chỉ gọi select()
và ex()
, bạn chỉ là đối phó với biến đối tượng bình thường và chỉ có mối quan tâm bộ nhớ bình thường thay vì quản lý bộ nhớ bằng tay. Bạn vẫn phải suy nghĩ về những lo ngại về bộ nhớ bình thường như bao nhiêu bộ nhớ đang được sử dụng bởi một mảng các đối tượng. Sau khi biến nằm ngoài phạm vi, hoặc bạn tự đặt nó thành null, nó trở nên có sẵn để thu thập rác để PHP xử lý điều đó cho bạn. Bạn có thể vẫn muốn đặt nó thành null trước khi nó hết phạm vi nếu mã của bạn không sử dụng nó nữa và có các thao tác theo sau nó sử dụng một lượng bộ nhớ không xác định như vòng lặp và các cuộc gọi hàm khác. Tôi không biết các bộ kết quả và các hàm hoạt động trên chúng được thực hiện như thế nào (và ngay cả khi tôi đã làm, điều này có thể thay đổi với các phiên bản PHP và MySQL tương lai khác), vì vậy có khả năng hàm select()
xấp xỉ gấp đôi số lượng bộ nhớ được sử dụng ngay trước khi mysql_free_result($rs)
được gọi. Tuy nhiên bằng cách sử dụng select() vẫn loại bỏ những gì chúng ta thường là mối quan tâm chính của ngày càng nhiều bộ nhớ được sử dụng trong vòng lặp và các cuộc gọi chức năng khác nhau. Nếu bạn lo lắng về khả năng sử dụng bộ nhớ đôi này và bạn chỉ làm việc với một hàng tại một thời điểm trong một lần lặp, bạn có thể tạo một hàm() sẽ không tăng gấp đôi mức sử dụng bộ nhớ của bạn và sẽ bảo vệ bạn khỏi suy nghĩ về mysql_free_result()
:
each($sql,$fun) {
$rs= query($sql);
while($o= mysql_fetch_object($rs))
$fun($o);
mysql_free_result($rs);
}
bạn có thể sử dụng nó như thế này:
each("SELECT * FROM users", function($user) {
echo $user->username."<BR>";
});
Một lợi thế của việc sử dụng mỗi() là nó không trả lại bất cứ điều gì, vì vậy bạn không cần phải suy nghĩ về việc liệu hoặc không đặt giá trị trả về thành null sau này.
Tôi chân thành hy vọng mã bạn trích dẫn chỉ để minh họa - tất cả điều này có thể được thực hiện trong một truy vấn SQL: INSERT INTO another_table (product_id, product_name) SELECT product_id, product_name FROM product – symcbean