Sự khác biệt giữa ++ $ i và $ i ++ trong PHP là gì?


82

Sự khác biệt giữa ++$i$i++trong PHP là gì?

Câu trả lời:


96

++$ilà trước tăng trong khi $i++sau tăng.

  • pre-increment: biến tăng itrước rồi mới hủy tham chiếu.
  • sau tăng: khử tham chiếu và sau đó tăng i

"Hãy tận dụng lợi thế của thực tế là PHP cho phép bạn tăng sau ($ i ++) và tăng trước (++ $ i). Tuy nhiên, ý nghĩa giống nhau miễn là bạn không viết bất cứ thứ gì như $ j = $ i ++. tăng trước nhanh hơn gần 10%, có nghĩa là bạn nên chuyển từ tăng sau sang tăng trước khi có cơ hội, đặc biệt là trong các vòng lặp chặt chẽ và đặc biệt nếu bạn đang hiểu biết về việc tối ưu hóa vi mô! " - TuxRadar

Để làm rõ thêm, sau tăng trưởng trong PHP đã được ghi nhận là lưu trữ một biến tạm thời thuộc tính chi phí 10% này so với tăng trước.


6
Đây có phải là quy tắc chung hay là PHP cụ thể.
Zoidberg

1
... nguồn được liệt kê trong câu trả lời của tôi. Tôi đã không kiểm tra nó ra bản thân mình ... Tôi đoán tôi có thể bằng cách nhìn vào mã nguồn của PHP mặc dù ...
jldupont

3
Bản thân tôi sẽ không khái quát sang một số ngôn ngữ khác.
jldupont

3
Việc tăng tốc độ tăng trước là đặc trưng của PHP do thực tế là tăng sau tạo ra một biến tạm thời, tạo ra chi phí.
Corey Ballou

4
@knittl Hãy nhớ rằng đó là 10% của (một người hy vọng) hoạt động rất nhanh :)
jensgram

66

++$igia số $i, nhưng đánh giá theo giá trị của $i+1 $i++gia số $i, nhưng đánh giá giá trị cũ của $i.

Đây là một ví dụ:

$i = 10;
$a = $i++;
// Now $a is 10, and $i is 11

$i = 10;
$a = ++$i;
// Now $a is 11, and $i is 11

Đôi khi có một chi phí kiểm định nhỏ cho việc sử dụng $i++. Hãy xem, khi bạn làm điều gì đó như

$a = $i++;

Bạn thực sự đang làm điều này:

$temporary_variable = $i;
$i=$i+1;
$a=$temporary_variable;

3
Đây là câu trả lời tốt hơn. Khái quát chung chung về những gì điều này làm mà không có các ví dụ mã là vô nghĩa. Những người ủng hộ cho những câu trả lời như vậy có thể là từ những người đã biết nó hoạt động như thế nào và do đó nghĩ rằng đó là những câu trả lời tuyệt vời.
James

Tôi chắc rằng có nhiều thứ hơn ở cấp độ thấp hơn, vì vậy câu hỏi này có thể được tranh luận. Nhưng tại sao PHP lại cần var temp? Tại sao không: $ a = $ i; $ i = $ i + 1;
Taylor Vance

@Taylor, Đó là một câu hỏi hay! Hãy thử thay thế $ i bằng một lệnh gọi hàm như thế này: $a=func()++và tự hỏi bản thân làm thế nào bạn có thể viết lại nó mà không có ++ và không gọi func () nhiều lần.
Shalom Craimer

43

++$i là tiền tăng

  1. $i được tăng dần
  2. giá trị mới được trả lại

$i++ là hậu gia tăng

  1. giá trị $iđược sao chép vào một biến tạm thời nội bộ
  2. $i được tăng dần
  3. bản sao nội bộ của giá trị cũ $iđược trả lại

14
++$i //first increment $i then run line
$i++ //first run line then increment $i 

Thats về mặt kỹ thuật một sự đơn giản hóa - nghĩ về một vòng lặp for, vv
Antony Carthy

11

trong trường hợp này không có sự khác biệt:

for($i = 0;$i<3;++$i)var_dump $i;
/*
int(0)
int(1)
int(2)
*/
for($i = 0;$i<3;$i++)var_dump $i;
/*
int(0)
int(1)
int(2)
*/

nhưng:

for($i = 0;$i<3; $j = ++$i )var_dump($j);
/*
NULL
int(1)
int(2)
*/
for($i = 0;$i<3; $j = $i++ )var_dump($j);
/*
NULL
int(0)
int(1)
*/

Điều này rất hữu ích, phần tăng tiền tố dường như ít gây ngạc nhiên nhất. Bây giờ tôi sẽ chuyển sang luôn sử dụng tăng tiền tố.
CMCDragonkai

8

ví dụ này chỉ đơn giản là

<?php 

$x = 10;  

echo $x++. ' '.$x;  // the result is 10 and 11

echo '<br>';

$y = 10;

echo ++$y. ' ' .$y; // the result is 11 and 11

// so the  $x++ is not showing +1 at first but the next time
// and the ++y is showing +1 first time but not increasing next

Cảm ơn vì ví dụ đơn giản. Giờ thì tôi đã hiểu.
Praditha

7

Sự khác biệt là: ++$isẽ tăng $ibiến và trả về giá trị cập nhật, trong khi $i++sẽ trả về giá trị ban đầu, vì vậy hãy tăng nó.

$prefix = 1;
$postfix = 1;
echo ++$prefix;   // 2
echo $postfix++;  // 1

5

Để giải thích quan điểm của jldupont:

$i = 1;
$x = $i++;
echo $x; // prints 1
$x = ++$i;
echo $x; // prints 3

4

Một cách khác để xem xét việc tăng trước và sau là viết tắt để kết hợp 2 câu lệnh.

Tăng trước

// long form
$y = $y + 1;
$x = $y; // any statement using $y

// shorthand
$x = ++$y; // the same statement using $y

Tăng sau

// long form
$x = $y; // any statement using $y
$y = $y + 1;

// shorthand
$x = $y++; // the same statement using $y

3

Nó có lẽ được minh họa tốt nhất bằng một ví dụ ...

Tăng sau:

$zero = 0;
$n = $zero++; //$n is zero

Tăng trước:

$zero = 0;
$n = ++$zero; //$n is one

3

Câu trả lời ngắn:

  • Tiền tố tăng giá trị và trả về giá trị đã tăng
  • Postfix tăng giá trị và trả về giá trị trước khi nó được tăng lên
  • Tiền tố nhanh hơn

Câu trả lời dài: Nếu bạn suy nghĩ một chút về nó, bạn sẽ tự thực hiện những điều đó như thế nào, bạn có thể sẽ nhận ra tại sao tiền tố lại nhanh hơn. Sự thật mà nói, postfix thực sự (thường) được triển khai bằng cách sử dụng tiền tố:

const T T::operator ++ (int) // postfix
    {
    T orig(*this);
    ++(*this); // call prefix operator
    return (orig);
    }

Tránh postfix trừ khi bạn có lý do cụ thể để không. Sự khác biệt về tốc độ có thể là khá nhiều đối với các kiểu dữ liệu phức tạp.

Tôi thực sự đã tìm kiếm điều này một vài ngày trước. Đây là nguồn của tôi.


3

Mục đích chính của toán tử tăng sau sửa chữa là sử dụng như sau:

while(*condition*)
    $array[$i++] = $something;

Đây là một cách rất thanh lịch, làm thế nào để có được một số lần lặp lại mảng. Phá vỡ:

  1. Biến $ cái gì đó sẽ được gán cho phần tử mảng được lập chỉ mục với $ i
  2. Biến $ i sẽ được tăng dần
  3. Lặp lại ở cuối, điều kiện sẽ được kiểm tra

Trong tất cả các trường hợp khác, bạn nên sử dụng toán tử tiền tố. Nó làm cho mã rõ ràng hơn nhiều (Bạn có thể chắc chắn rằng bạn đã làm việc với giá trị gia tăng của biến cụ thể).


Được ủng hộ vì đề xuất sử dụng tiền tố trừ khi cần phải có hậu tố.
developerbmw

3

$ i ++ được gọi là tăng sau. Nó chỉ tăng giá trị của $ i sau khi gán giá trị gốc của $ i cho $ j trước.

++ $ i được gọi là số tăng trước. Nó tăng giá trị của $ i trước khi gán giá trị cho $ j, vì vậy giá trị cập nhật của $ i sẽ được gán cho $ j.

Vì thế,

$i = 4;
$j = $i++;
// Now, $i = 5 and $j = 4

$i = 4;
$j = ++$i;
// Now, $i = 5 and $j = 5

Những lý thuyết này cũng áp dụng theo cách tương tự để giảm dần.

Hi vọng điêu nay co ich!


0

Tôi đã chạy mã sau để kiểm tra xem ++ $ i có nhanh hơn $ i ++ 10% hay không. Tôi thừa nhận, mã không có một kết quả ổn định nhưng ngay cả khi đó, ít nhất tôi cũng nên thấy một số con số gần 10%. Mức cao nhất mà tôi nhận được là khoảng 4-4,5%.

<?php

$randomFloat = rand(0, 10) / 10;

$before1 = microtime(true);

for($i=0; $i <1000000; ++$i){
    $rand = (rand(0, 10) / 10) * (rand(0, 10) / 10);
}

$after1 = microtime(true);
echo 'it took '.($after1-$before1) . ' seconds fot ++$i<br />';

$before2 = microtime(true);

for($i=0; $i <1000000; $i++){
    $rand = (rand(0, 10) / 10) * (rand(0, 10) / 10);
}

$after2 = microtime(true);
echo 'it took '.($after2-$before2) . ' seconds fot $i++<br /><br />';

echo '++$i is '.((($after1-$before1)*100)/($after2-$before2)-100).'% faster than $i++';

-1

Cả hai toán tử vẫn thực hiện những gì mà cú pháp của chúng ngụ ý: tăng dần. Bất kể tiền tố hay hậu tố, biến chắc chắn sẽ được tăng thêm 1. Sự khác biệt giữa hai biến này nằm ở giá trị trả về của chúng.

1. Số tăng tiền tố trả về giá trị của một biến sau khi nó đã được tăng.

2. Mặt khác, số tăng hậu tố được sử dụng phổ biến hơn trả về giá trị của một biến trước khi nó được tăng.

// Prefix increment

let prefix = 1;
console.log(++prefix); // 2

console.log(prefix); // 2

// Postfix increment

let postfix = 1;

console.log(postfix++); // 1

console.log(postfix); // 2

Để ghi nhớ quy tắc này , tôi nghĩ về cú pháp của cả hai. Khi một người nhập số tăng tiền tố, người ta nói ++ x. Vị trí của ++ là quan trọng ở đây. Nói ++ x có nghĩa là tăng (++) trước rồi trả về giá trị của x, do đó chúng ta có ++ x. Việc tăng hậu tố hoạt động ngược lại. Nói x ++ có nghĩa là trả về giá trị của x trước rồi tăng (++) nó sau, do đó x ++.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.