SORU
2 Ocak 2013, ÇARŞAMBA


İnş evresel C 11 anlamına mı geliyor?

const anlamına geldiğini duydumiş parçacığı güvenliC 11. Bu doğru mu?

const şimdi eşdeğer olduğu anlamına gelmezJava'5* s *?

Dışarı koşuyorlaranahtar kelimeler?

CEVAP
2 Ocak 2013, ÇARŞAMBA


const anlamına geldiğini duydumiş parçacığı güvenliC 11. Bu doğru mu?

birazdoğru...

Bu nedirStandart Diliş parçacığı güvenliği üzerine söyleyecek çok şey var:

[1.10/4] İki ifade değerlendirmelerçatışmaeğer onlardan biri bir bellek konumu (1.7) ve diğer değiştirirse, bir veya aynı bellek konumuna erişen değiştirir.

[1.10/21] Bir programın çalışmasını içerirveri yarışıeğer farklı konuları birbiriyle çelişen iki eylemleri varsa, atomik olmayan, ve de en az bir diğeri önce oluyor. Bu tür bilgiler yarış tanımsız davranış oluşur.

için yeterli bir koşul başka bir şey değildirveri yarışıgerçekleşmesi için:

  1. İki veya daha fazla eylem belirli bir şey üzerinde aynı anda gerçekleştirilmekte; ve
  2. Bunlardan en az birini yazma.

Standart Kütüphaneoluşturur, biraz daha ileri giderek:

[17.6.5.9/1] Bu bölümde uygulamaları veri yarışları (1.10) önlemek için karşılayacak gereksinimleri belirtir. Her standart kütüphane fonksiyonu aksi belirtilmediği sürece her ihtiyacını karşılamak zorundadır. Uygulamaları haller aşağıda belirtilen farklı veri yarışları engelleyebilir.

[17.6.5.9/3] Standart kütüphane fonksiyonu olan nesneleri doğrudan ya da dolaylı olarak erişilen sürece doğrudan ya da dolaylı olarak nesneleri (1.10) geçerli iş parçacığı iş parçacığı dışındaki kişiler tarafından erişilebilir değiştirmeyecektir bir C işlevi yoluyla olmayaninşbağımsız değişkenler, this dahil olmak üzere.

basit bir deyişle const nesneler üzerinde işlem için beklediğini söylüyoriş parçacığı güvenli. Bu anlamına gelirStandart Kütüphaneveri bir yarış olduğu sürece kendi türleri const nesneler ya . operasyon olarak tanıştırmayacak

  1. Tamamen okur ibarettir, yani hiçbir yazar--; ya
  2. DAHİLİ olarak eşitler yazar.

Eğer bu beklenti türlerinden biri için geçerli değilse, o zaman doğrudan veya dolaylı olarak birlikte herhangi bir bileşeni ile kullanmaStandart Kütüphanebir neden olabilirveri yarışı. Sonuç, const demekiş parçacığı güvenliStandart Kütüphanebakış açısı. Önemli bu sadece bir olduğunu unutmayınsözleşmeve olursa olsun Eğer onu kırarsan derleyici tarafından zorlanan, olmayacaktanımsız davranışve tek başınasınız. const mevcut veya kod oluşturma etkilemez değil olsa bile en azından saygı değilveri yarışları--.

const şimdi eşdeğer olduğu anlamına gelmezJava'13 *s*?

Hayır. Hiç de değil

Temsil eden bir dikdörtgen: aşırı basitleştirilmiş aşağıdaki sınıf düşünün

class rect {
    int width = 0, height = 0;

public:
    /*...*/
    void set_size( int new_width, int new_height ) {
        width = new_width;
        height = new_height;
    }
    int area() const {
        return width * height;
    }
};

üye işleviareaiş parçacığı güvenli; ** 16 yaşında, onun değil çünkü ama tamamen okuma işlemleri içerir çünkü. İşin içinde yazar yok, ve en az bir yer yazmak için gereklidirveri yarışıortaya. İstediğin ve doğru sonuçlar her zaman alacak kadar çok iş parçacığı area çağrı anlamına gelir.

Bu rect olduğu anlamına gelmez unutmayıniş parçacığı güvenli. Aslında, kolay görmek için nasıl eğer bir çağrı area olursa aynı anda bir çağrı set_size verilen rect area diye sonuna kadar bilgi işlem sonucuna göre bir eski bir yeni genişlik ve yükseklik (hatta bozuk değerler).

Ama bu sorun değil, hatta olması beklenen çok mu const değiliş parçacığı güvenlisonuçta. Bir nesne const rect öte yandan, olacaklarını ifade ettiiş parçacığı güvenlihayır mümkün yazar const_cast-ıng düşünüyorsanız bir şey aslında const ilan etmesinden sonra. (ve o zamandan beri ^em>tanımsız davranışve bu).

Bu ne anlama geliyor o zaman?

Hadi hatırın çarpma işlemleri çok pahalı olduğu için aralarında varsayalım ve biz daha iyi mümkün olduğunca uzak duruyorum. İstenen ve daha sonra yine talep olması halinde önbellek gelecekte yalnızca, alan hesaplama yapabiliriz:

class rect {
    int width = 0, height = 0;

    mutable int cached_area = 0;
    mutable bool cached_area_valid = true;

public:
    /*...*/
    void set_size( int new_width, int new_height ) {
        cached_area_valid = ( width == new_width && height == new_height );
        width = new_width;
        height = new_height;
    }
    int area() const {
        if( !cached_area_valid ) {
            cached_area = width;
            cached_area *= height;
            cached_area_valid = true;
        }
        return cached_area;
    }
};

Eğer bu örnek çok yapay görünüyor, zihinsel int ile değiştirinçok büyük bir dinamik olarak atanan bir tamsayıdoğuştan olaniş parçacığı güvenlive çarpım oldukça maliyetli.]

üye işleviarea artıkiş parçacığı güvenlişimdi yazar yapıyor ve dahili olarak eşitlenir. Bir sorun olur mu? area çağrısı bir parçası olarak ortaya çıkabilirkopya-yapıcıbaşka bir nesne gibikurucubir üzerinde bir işlem tarafından çağrıldıstandart konteynerve bu noktadastandart kütüphanebu işlemi bir çarpışma bekliyorokuyunaçısındanveri yarışları. Ama yazar yapıyoruz!

Bir rect koyar koymazstandart konteynerdoğrudan veya dolaylı olarak ... ... giriyoruzsözleşmeileStandart Kütüphane. Hala sözleşme onurlandıran iken yazar yapıyor const bir işlevi tutmak için, içten yazıyor: o eşitlemek için ihtiyacımız var

class rect {
    int width = 0, height = 0;

    mutable std::mutex cache_mutex;
    mutable int cached_area = 0;
    mutable bool cached_area_valid = true;

public:
    /*...*/
    void set_size( int new_width, int new_height ) {
        if( new_width != width || new_height != height )
        {
            std::lock_guard< std::mutex > guard( cache_mutex );

            cached_area_valid = false;
        }
        width = new_width;
        height = new_height;
    }
    int area() const {
        std::lock_guard< std::mutex > guard( cache_mutex );

        if( !cached_area_valid ) {
            cached_area = width;
            cached_area *= height;
            cached_area_valid = true;
        }
        return cached_area;
    }
};

area işlevi yaptık unutmayıniş parçacığı güvenlirect hala değil , amaiş parçacığı güvenli. Bir arama area oluyor aynı anda arama set_size may hala sonunda bilgisayar yanlış değer beri atamaları için width height değil tarafından korunan, zaman uyumu.

Biz gerçekten istedimiş parçacığı güvenlirect, bir eşitleme korumak için ilkel kullanırıznon-thread-saferect.

Dışarı koşuyorlaranahtar kelimeler?

Evet, onlar. Çalışan varanahtar kelimelerilk günden beri.


Kaynak: You don't know const and mutable -Herb Sutter

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • ecf150king

    ecf150king

    20 Ocak 2006
  • jonathepianist

    jonathepiani

    31 Temmuz 2008
  • Michael Neal

    Michael Neal

    2 Mayıs 2009