Yapmak özel bir tür "tie-mümkün" (std ile uyumlu kravatı)
Ben özel bir türü uzatabilirim) göz önünde bulundurun:
struct Foo {
int a;
string b;
};
Nasıl bu nesnenin bir örneğini başvuruları std::tie
, std::tuple
yani atanabilir yapabilir miyim?
Foo foo = ...;
int a;
string b;
std::tie(a, b) = foo;
Başarısız girişim:
tuple<int&,string&> = Foo
atama operatörünü aşırı yükleme atama operatörü sol taraftaki üyeleri nesnesi olmak zorunda olan ikili operatörlerinden biri olduğu için, mümkün değildir.
Uygun bir uygulama ile bunu çözmeye çalıştımdemet dönüşüm operatör. Aşağıdaki sürümleri başarısız:
operator tuple<int,string>() const
operator tuple<const int&,const string&>() const
Atama bir hata, bunu söylemeye neden "operator =
tuple<int&,string&> = Foo
aşırı değildir". Bu nedenle sanırım "dönüşüm her tür X şablon parametre deducing X operatörün=" birlikte iş yapma, aynı anda sadece bir tanesi.
Eksik teşebbüs:
Dolayısıyla dönüşüm operatörü uygulamaya çalıştımkravat tam yazın:
Atama şimdi türleri artık (dönüşüm sonra) tam olarak aynı beri çalışıyor, ama bu destek olmasını isterdim üç senaryo için işe yaramaz:
- Eğer kravat farklı ama Cabrio türleri bağımlı değişken (
int a;
long long a;
istemci tarafında, yani değişim) varsa, türleri tam olarak aynı olması beri başarısız. Bu Cabrio tipleri sağlayan başvurular bir demet bir demet atama olağan kullanım çelişmektedir.(1) - Dönüşüm operatör başvuruları lvalue verilecek olan bir kravat dönmek gerekiyor. Bu geçici değerleri veya sabit üyeleri için işe yaramaz.(2)
- Eğer dönüşüm operatör sabit değilse, Atama da sağ el
const Foo
bir taraf için başarısız olur. Dönüşüm sabit bir sürüm uygulamak için, sabit-lik sabit konu üyelerinden uzakta kesmek için ihtiyacımız var. Bu çirkin ve tanımsız davranış sonucu kötü olabilir.
Ben sadece bir alternatif sunmak benim kendi tie
fonksiyon sınıfı ile birlikte benim "tie-mümkün" nesneler, kendimi zorlamak için yinelenen işlevselliği std::tie
Bu hoşuma gitmedi o değil de ben bulmak zor öyle geliyor ama yanlış yapmak zorunda).
Günün sonunda, sonuç bu kütüphane sadece başlığın bir uygulama için bir dezavantaj olduğunu düşünüyorum. Olmalarını istediğimiz kadar sihirli değiller.
DÜZENLEME:
Görünüşe göre, gerçek bir çözüm yukarıdaki tüm sorunları bir konuşma yok. Çok iyi bir cevap bu çözülebilir olmadığını açıklıyor. Özellikle, biri "başarısız girişim" işe yaraması mümkün değil. neden biraz ışık tutmak istiyorum
(1): korkunç kesmek için bir şablon olarak dönüştürme, yazma ve dönüştürme operatörü istenen üyesi türleri dönüştürmek için. Bu dönüştürülmüş üyeleri depolamak için nerede bilmiyorum çünkü korkunç bir hack. this demo statik değişkenleri kullanıyorum, ama bu iş parçacığı evresel değildir.
(2): hack (1) uygulanabilir.
CEVAP
Mevcut girişimleri neden başarısız
std::tie(a, b)
std::tuple<int&, string&>
üretir.
Bu tür std::tuple<int, string>
vb ile ilgili değildir.
std::tuple<T...>
birkaç atama operatörleri: var
- Gereken atama-operatör, bir
std::tuple<T...>
varsayılan - Bir demet dönüştürme atama operatörüşablonbir tür parametresi ile
std::tuple<U...>
alırU...
, paketi - Bir çift-dönüştürme atama operatörüşabloniki tür parametreleri ile
U1, U2
std::pair<U1, U2>
alır
Bu üç sürümleri için mevcut kopyalama ve türevleri hareket; aldıkları türleri de const&
&&
ekleyin.
Atama operatörü şablonları işlev bağımsız değişken türü (OLUŞTURDUĞU türü yani atama-ifade) şablon onların argümanları anlamak için.
Foo
, hiçbiri, dönüşüm operatör olmadan atama operatörleri std::tie(a,b) = foo
için geçerli.
Eğer Foo
,dönüştürme operatörü eklerseniz
o zaman sadece varsayılan atama-operatör uygun olur:
Kesintinin almaz şablonu tarafından tanımlanan kullanıcı hesabı içine dönüşüm.
Yani, atama-operatör türü şablonları Foo
anlamak için şablon bağımsız olamaz.
Tek bir kullanıcı tanımlı beri örtülü dönüşüm dönüşüm bir dizi izin verilir, dönüşüm operatör dönüştürür türü varsayılan atama türünü tam olarak eşleşmesi gerekir. Yani, std::tie
sonuç olarak aynı satır öğesi türleri kullanmak gerekir.
Öğe türleri (long
Foo::a
örneğin atama), Foo
dönüştürme operatör dönüşümleri desteklemek için bir şablon yapmak gerekiyor
struct Foo {
int a;
string b;
template<typename T, typename U>
operator std::tuple<T, U>();
};
Ancak, std::tie
öğe türlerini ifade etmektedir.
Geçici bir başvuru döndürmek gerekir beri,
operatör şablon içinde dönüşüm için seçenekler oldukça sınırlıdır
(öbek, türü punning, statik, iş parçacığı yerel, vb.).
özel durum "ben İllegalStateExcep...
Ne'un farkı ise <meta http-eşd...
Bu ne anlama geliyor? &;'NSUnknow...
Nasıl "düzgün" JavaScript öz...
Kullanarak " koyuyorsun;sayfa özel...