Cppreference için şu örnek kod vardır std::transform
:
std::vector<std::size_t> ordinals;
std::transform(s.begin(), s.end(), std::back_inserter(ordinals),
[](unsigned char c) -> std::size_t { return c; });
Ancak şunu da söylüyor:
std::transform
unary_op
veya 'nın siparişe göre uygulanmasını garanti etmezbinary_op
. Bir diziye sırayla bir işlev uygulamak veya bir dizinin öğelerini değiştiren bir işlevi uygulamak için kullanınstd::for_each
.
Bu muhtemelen paralel uygulamalara izin vermek içindir. Bununla birlikte, üçüncü parametresi aşağıdaki son koşula sahip olan std::transform
bir a parametresidir :LegacyOutputIterator
++r
Bu işlemin
r
artırılabilir olması gerekmez ve önceki değerinin herhangi bir kopyasınınr
artık silinemez veya artırılabilir olması gerekmez.
Bu yüzden çıkış atama geliyor bana gereken sırayla olur. Uygulamanın düzensiz unary_op
olabileceği ve geçici bir yerde saklanabileceği, ancak sırayla çıktıya kopyalanabileceği anlamına mı geliyor? Bu hiç yapmak isteyeceğiniz bir şey gibi gelmiyor.
Çoğu C ++ kütüphanesi aslında paralel yürütücüler uygulamamıştır, ancak Microsoft uygulamıştır. Ben eminim bu ilgili kod ve ben düşünüyorum o çağıran bu populate()
fonksiyonu elbette çünkü yapmak için geçerli bir şey değildir çıktı, parçaları rekor Yineleyicilerin için LegacyOutputIterator
kopyalarını artırarak geçersiz edilebilir.
Neyi kaçırıyorum?
s
yineleyicileri geçersiz kılan kodunuz yanlış .
std::transform
zorla alma politikası ile daha sonra rasgele erişim yineleyici gereklidir hangi back_inserter
yerine getiremez. IMO tarafından belirtilen parça dokümantasyonu bu senaryoyu ifade eder. Doküman kullanımındaki örneğe dikkat edin std::back_inserter
.
transform
sürümü ile paralelliği kullanıp kullanmayacağınıza karar verir.transform
Büyük vektörler için başarısız olur.