2013-09-03 32 views
11

mã của tôi cho một trò chơi kéo giấy đá (gọi là tung) như sau:ReferenceError: Invalid phía bên tay trái trong phân

var toss = function (one,two) { 
    if(one = "rock" && two = "rock") { 
     console.log("Tie! Try again!"); 
    } 
    // more similar conditions with `else if` 
}; 

Khi tôi nhập vào các thông số

toss("rock","rock") 

tôi nhận được mã lỗi này:

"ReferenceError: Invalid left-hand side in assignment"

Cách khắc phục? Lỗi này có nghĩa là gì và những trường hợp nào khác khi lỗi này có thể xảy ra?

+0

Ba "trói" các trường hợp có thể được đơn giản hóa thành một đơn 'nếu (một == hai)' –

Trả lời

35

Bạn phải sử dụng == để so sánh (hoặc thậm chí ===, nếu bạn muốn so sánh các loại). Một đơn = dành cho bài tập.

if (one == 'rock' && two == 'rock') { 
    console.log('Tie! Try again!'); 
} 
+3

tôi là một đồ ngốc .... ....cảm ơn! – Kevin

+0

để làm rõ, sự khác biệt giữa == và === là gì? – Kevin

+0

Nhận xét ở trên là sai, ECMA xác định rằng đây không phải là kiểm tra kiểu, nó thực hiện một thao tác gọi là loại cưỡng chế. Điều này thực sự hữu ích khi biết, xem câu trả lời này http://stackoverflow.com/questions/19915688/what-exactly-is-type-coercion-in-javascript – VladNeacsu

1

Lý do thường gặp các lỗi:

  • sử dụng chuyển nhượng (=) thay vì bình đẳng (==/===)
  • gán là kết quả của chức năng foo() = 42 thay vì lập luận đi qua (foo(42))
  • chỉ thiếu tên thành viên (ví dụ: giả sử một số lựa chọn mặc định): getFoo() = 42 thay vì getFoo().theAnswer = 42 hoặc chỉ mục mảng ing getArray() = 42 thay vì getArray()[0]= 42

Trong trường hợp này bạn muốn sử dụng == (hoặc tốt hơn ===-What exactly is Type Coercion in Javascript?) để kiểm tra đẳng thức (như if(one === "rock" && two === "rock"), nhưng nó trở thành lý do thực tế bạn đang nhận được lỗi này là phức tạp hơn.

Lý do lỗi là Operator precedence. Đặc biệt, chúng tôi đang tìm kiếm && (ưu tiên 6) và = (ưu tiên 3).

Hãy đặt dấu ngoặc trong biểu thức theo ưu tiên - && cao hơn = vì vậy nó được thực hiện đầu tiên tương tự như cách người ta sẽ làm gì 3+4*5+6 như 3+(4*5)+6:

if(one= ("rock" && two) = "rock"){... 

Bây giờ chúng ta có biểu hiện tương tự như nhiều bài tập như a = b = 42 do liên kết từ phải sang trái được thực hiện dưới dạng a = (b = 42). Vì vậy, bổ sung thêm niềng răng:

if(one= ( ("rock" && two) = "rock") ){... 

Cuối cùng chúng tôi đến để vấn đề thực tế: ("rock" && two) không thể được đánh giá để l-giá trị có thể được giao cho (trong trường hợp đặc biệt này nó sẽ được giá trị của two như truthy) .

Lưu ý rằng nếu bạn sử dụng niềng răng để khớp với mức độ ưu tiên nhận thấy xung quanh mỗi "bình đẳng" với niềng răng, bạn sẽ không bị lỗi.Rõ ràng đó cũng sản xuất kết quả khác nhau hơn bạn mong muốn - thay đổi giá trị của cả hai biến và hơn làm && trên hai chuỗi "rock" && "rock" dẫn đến "rock" (mà trong lần lượt là truthy) tất cả các thời gian do hành vi của logial &&:

if((one = "rock") && (two = "rock")) 
{ 
    // always executed, both one and two are set to "rock" 
    ... 
} 

Đối thậm chí thêm chi tiết về các lỗi và các trường hợp khác khi nó có thể xảy ra - xem đặc điểm kỹ thuật:

Assignment

LeftHandSideExpression = AssignmentExpression
...
Throw a SyntaxError exception if the following conditions are all true:
...
IsStrictReference(lref) is true

Left-Hand-Side Expressions

The Reference Specification Type giải thích IsStrictReference:

... function calls are permitted to return references. This possibility is admitted purely for the sake of host objects. No built-in ECMAScript function defined by this specification returns a reference and there is no provision for a user-defined function to return a reference...

Các vấn đề liên quan