Urutan kelas operan dan enum(int) saat membebani operator di C#

Dalam C++ urutan evaluasi operan tidak ditentukan, apa yang perlu saya waspadai ketika saya mencoba membebani operator di C#.

class A{

  public static A operator +(A left, int right){
    left.someVariable += right;
    return left;
  }

  public static A operator +(A left, B right){
    var x = 1<<right; // Just to clarify that it might not be a simple int + int operation
    left.someVariable += x;
    return left;
  }
}
enum B{a=0,b=1,c=2}

var a = new A()+B.a+B.b+B.c;//I want this to be operator+(A,1<<0 + 1<<1 + 1<<2)
var b = (new A()+B.a)+B.b+B.c;//as well as this
var c = ((new A()+B.a)+B.b)+B.c;//and this

Resharper memberi tahu saya bahwa saya dapat menghapus tanda kurung di var b=... dan var c=..., tetapi saya tidak yakin apakah itu benar, karena saya tidak yakin apakah dijamin untuk selalu memanggil operator yang kelebihan beban +(A,B) dan tidak mengevaluasi ini sebagai suatu tempat

var d = new A()+((int)B.a+((int)B.b+(int)B.c)); //operator+(A, 0+1+2)

Perbarui

Berikut ini adalah spesifikasi bahasa C dan tidak berlaku untuk C# seperti yang ditunjukkan oleh PetSerAl.

Bacaan: Prioritas dan Urutan Evaluasi Saya cukup yakin a,b,c tidak dijamin akan dievaluasi dari kiri ke kanan.

Arah evaluasi tidak mempengaruhi hasil ekspresi yang menyertakan lebih dari satu operator perkalian (*), penjumlahan (+), atau biner-bitwise (& | ^) pada level yang sama. Urutan operasi tidak ditentukan oleh bahasa. Kompiler bebas mengevaluasi ekspresi tersebut dalam urutan apa pun, jika kompiler dapat menjamin hasil yang konsisten.


person Kevin Streicher    schedule 28.09.2017    source sumber
comment
Di C# + memiliki asosiatif kiri, jadi a+b+c setara dengan (a+b)+c. Tapi, IMHO, yang lebih penting: operator tidak boleh membuat perubahan nyata dalam argumen.   -  person user4003407    schedule 28.09.2017
comment
@PetSerAl, tetapi bukankah teks yang dikutip dari situs msdna secara eksplisit mengatakan ini tidak berlaku untuk lebih dari satu operator tambahan pada tingkat yang sama?   -  person Kevin Streicher    schedule 28.09.2017
comment
Kutipan itu berasal dari bahasa C, tetapi bukan C#.   -  person user4003407    schedule 28.09.2017
comment
@PetSerAl terkadang saya merasa sangat bodoh. Saya membacanya - tetapi tidak memprosesnya. Jika Anda mempostingnya sebagai jawaban, saya akan menerimanya.   -  person Kevin Streicher    schedule 29.09.2017


Jawaban (1)


Dari Draf akhir ECMA edisi ke-2

Ketika operan terjadi antara dua operator dengan prioritas yang sama, asosiatif operator mengontrol urutan operasi yang dilakukan: * Kecuali untuk operator penugasan dan operator penggabungan nol, semua operator biner bersifat asosiatif kiri, artinya operasi tersebut dilakukan dari kiri ke kanan.

x + y + z

dievaluasi sebagai

(x + y) + z.

  • Operator penugasan, operator penggabungan nol, dan operator kondisional (?:) bersifat asosiatif kanan, artinya operasi dilakukan dari kanan ke kiri.

x = y = z

dievaluasi sebagai

x =(y= z).

Prioritas dan asosiatif dapat dikontrol menggunakan tanda kurung.

x + y * z

pertama kalikan y dengan z lalu tambahkan hasilnya ke x, tapi

(x + y) * z

pertama tambahkan x dan y lalu kalikan hasilnya dengan z.

person Kevin Streicher    schedule 29.09.2017