Soru 2 “şamandıra” kullanarak “çifte” öykün.


Yalnızca 32 bit tek kesinlikli kayan nokta aritmetiğini destekleyen yerleşik bir donanım için bir program yazıyorum. Ancak, uyguladığım algoritma, 64 bitlik çift duyarlıklı bir ekleme ve karşılaştırma gerektirir. Taklit etmeye çalışıyorum double datatype iki kişilik bir tuple kullanarak floats. Yani double d olarak taklit edilecek struct tuple içeren: (float d.hi, float d.low).

Karşılaştırma, sözlükbilgisel bir sıralama kullanılarak açık olmalıdır. Ek ancak biraz zor çünkü hangi tabanı kullanmam gerektiğinden emin değilim. Olmalı mı FLT_MAX? Ve nasıl bir taşıma saptayabilirim?

Bu nasıl yapılabilir?


Düzenle (Berraklık): Ekstra alan yerine ekstra anlamlı rakamlara ihtiyacım var.


52
2017-07-20 23:53


Menşei


Ekstraya ihtiyacın var mı menzil arasında doubleya da sadece ekstra önemli basamaklar? - dan04
Ekstra önemli basamaklara ihtiyacım var.
O zaman sahip olduğunuz değerlerin aralığı nedir? Üstelik, üstelik büyük ölçüde farklılık gösterip göstermediği büyük bir fark yaratıyor. Hepsi benzer bir aralıkta ise, belki de sabit nokta matematik kullanabilirsiniz. Özellikle sadece ekleme ve karşılaştırmaya ihtiyacınız varsa, sabit nokta gitmenin yolu olabilir. - Rudy Velthuis
Üstelik büyük ölçüde farklılık gösterir. 1e-3, 1e + 10 ve 1e + 20 civarında neredeyse üç ayrı aralık var.
@ M.S: Bu çok büyük bir aralık gibi görünüyor double hassas. özellikle, 1.0E+20 ve 1.0E-03 epsilon'dan daha fazla farklılık gösterir double bu tipik olarak 1.0E-16 ya da öylesine) bu gibi işlemleri beklerdim 1.0E+20 + 1.0E-03 eşit olurdu 1.0E+20, kullanırken bile double. Bu bir sorun olur mu? - Darren Engwirda


Cevaplar:


çift-şamandıra, tek duyarlıklı aritmetik hassasiyetinin neredeyse iki katını elde etmek için tek hassasiyetli sayı çiftlerini kullanan bir tekniktir. Tek hassasiyetli üs aralığının (aralığın alt uçlarındaki ara akış ve aşırı akış nedeniyle) küçük bir azalma ile birlikte . Temel algoritmalar T.J. 1970'lerde Dekker ve William Kahan. Aşağıda, bu tekniklerin GPU'lara nasıl uyarlanabileceğini gösteren oldukça yakın tarihli iki makale listeleniyor, ancak bu kağıtlarda kapsanan malzemelerin çoğu, platformdan bağımsız olarak uygulanabilir.

http://hal.archives-ouvertes.fr/docs/00/06/33/56/PDF/float-float.pdf Guillaume Da Graça, David Defour Float-float operatörlerinin grafik donanımı üzerinde uygulanması, Gerçek Sayılar ve Bilgisayarlar 7. konferans, RNC7.

http://andrewthall.org/papers/df64_qf128.pdf Andrew Thall GPU Hesaplaması için Genişletilmiş Hassas Kayan Nokta Numaraları.


72
2017-07-21 01:17



+1 diğer cevaplardan farklı olarak, bu aslında OP'nin sorusunu ele alır ve ilgili makalelere çok iyi bağlantılar verir. - R..
Mükemmel! Sadece benim için bir yol arıyordum. constexpr Fonksiyonlar daha hassastır ve ilk bağlantıdaki fonksiyonları uygulamak için sadece yarım saat sürdü. - Slava P


Bu basit olmayacak.

Bir şamandıra (IEEE 754 tek hassasiyetli) 1 işaret biti, 8 bileşen biti ve 23 bit mantis (iyi, etkili 24) içerir.

Bir çift (IEEE 754 çift duyarlıklı) 1 işaret biti, 11 üs biti ve 52 bit mantis (etkili 53) içerir.

Şamandıralarınızdan birinden işaret biti ve 8 üssü bitlerini kullanabilirsiniz, ancak 3 tane daha üs bit ve 29 tane mantis diğerinden nasıl çıkacaksınız?

Belki başka biri zekice bir şeyle gelebilir, ama cevabım "bu imkansız". (Ya da en azından, "64 bit bir yapı kullanıp kendi işlemlerinizi uygulamaktan daha kolay değil")


11
2017-07-21 00:02



kullanma şamandıra-şamandıra Teknik, çiftin menzilini ve hassasiyetini elde edemez, ancak eski CUDA veya ARM CPU'lar gibi sadece donanım float aritetiği olması durumunda yazılım çiftinden çok daha hızlı ve çok daha hızlıdır - phuclv


Ne tür işlemler yapmak istediğinize bağlı. Sadece eklemeler ve çıkarmalardan hoşlanıyorsanız, Kahan Summation harika bir çözüm olabilir.


6
2017-07-21 00:51



Duymadığım +1 ilginç teknik. Onun girişleri ile başlamak için ekstra hassasiyet gerekiyor olsa da (emin değilim) yardımcı olmaz. - phkahler


Hem hassaslığa hem de geniş bir aralığa ihtiyacınız varsa, çift hassas kayan nokta gibi bir yazılım uygulamasına ihtiyacınız olacaktır. SoftFloat.

(Ek olarak, temel ilke, her bir değerin temsilini (örn. 64 bit) üç uzlaşmacı parçaya (işaret, üs ve mantis) kırmak, sonra da bir bölümün mantrisini üslerdeki farka bağlı olarak değiştirmek, veya diğer parçaların mantislerinden işaret bitlerine dayanarak çıkar ve olasılıkla mantisayı değiştirerek ve üssü buna göre ayarlayarak sonucu yeniden normale sokar.Yakın zamanda gereksiz kayıplardan kaçınmak için hesaba katılacak pek çok detay vardır. doğruluk, ve sonsuzluklar, NaNs ve denormalised numaraları gibi özel değerler ile uğraşmak.)


5
2017-07-21 00:47





Bu pratik değil. Öyleyse, her gömülü 32bit işlemci (veya derleyici) bunu yaparak çift duyarlıklı öykünür. Öyle olduğu gibi, farkında olduğum hiçbiri yok. Çoğu sadece iki kişilik yüzer yerine geçer.

Dinamik aralığa değil hassaslığa ihtiyacınız varsa, en iyi bahsiniz sabit nokta kullanmak olacaktır. Derleyici 64bit'i destekliyorsa, bu daha kolay olacaktır.


3
2017-07-21 00:10



Ekstra aralığa ihtiyaç olmaması durumunda aslında çok pratik double ve yaygın olarak kullanılmıştır eski NVIDIA CUDA GPU'ları onlar ne zaman desteklemedim double veya bazı derleyiciler için yakın dörtlü duyarlıklı donanım desteği mevcut olmadığında - phuclv


23 büyüklüğün üzerinde yüksek hassasiyet için tüm kısıtlamalar göz önüne alındığında, en verimli yöntem özel bir aritmetik paketi uygulamak olacağını düşünüyorum.

Kısa bir anket Briggs'i gösteriyor doubledouble C ++ kütüphanesi ihtiyaçlarınızı ve daha sonra bazılarını ele almalıdır. Görmek bu. [*] Varsayılan uygulama esas alınmıştır double 30 anlamlı rakam hesaplama elde etmek için, ama kullanımı için yeniden yazılmıştır float 13 veya 14 anlamlı rakam elde etmek için. Benzer büyüklük değerlerine sahip toplama işlemlerini ayırmak için yalnızca son işlemlerde uçları bir araya getirmek için özen gösterilirse, bu sizin ihtiyaçlarınız için yeterli olabilir.

Yine de, yorumlar x87 kontrol sicili ile uğraşmadan bahsetti. Ayrıntıları kontrol etmedim, ancak bu kod kullanımınız için çok taşınabilir değil.


[*] C ++ kaynağı bu yazıyla bağlantılı, ancak sadece gziplenmiş katran ölü bir bağlantı değildi.


3
2017-07-21 01:43





Kullanılabilecek başka bir yazılım tabanlı çözüm: GNU MPFR
Diğer birçok özel durumla ilgilenir ve aksi takdirde kendinize dikkat etmeniz gereken keyfi bir hassasiyete (64-bit çifte daha iyi) izin verir.


1
2017-07-21 11:43



O gerçekten keyfi keyfi gerektirmezse (46-bit hassasiyet yeterlidir) o zaman MPFR fazladır - phuclv


Bu benzer çift-çift aritmetik birçok derleyici tarafından long double sadece donanıma sahip bazı makinelerde double hesaplama desteği. Ayrıca, yok olduğu eski NVIDIA GPU'larında yüzer şamandıra olarak kullanılır. double destek. Bu şekilde hesaplama, bir yazılım kayan nokta kitaplığından çok daha hızlı olacaktır.

Ancak çoğu mikrodenetleyicide, donanım desteği yoktur. floatBu yüzden sadece yazılımda uygulanmaktadır. Bundan dolayı, kullanarak float-float Performansı artırmayabilir ve ekstra baytlık baytı kaydetmek için bazı bellek yüklerini ekleyebilir.

Gerçekten uzun mantislere ihtiyacınız varsa, özel bir kayan nokta kütüphanesi kullanmayı deneyin. Sizin için yeterli olanı seçebilirsiniz, örneğin kütüphaneyi sadece 40 bitlik mantis ve 7 bitlik bir üsse ihtiyaç duyuyorsanız, yeni 48-bit'lik float tipini adapte edecek şekilde değiştirin. Gereksiz 16 bit'i hesaplamak / saklamak için zaman harcamaya gerek yok. Fakat bu kütüphane çok verimli olmalıdır çünkü derleyici kütüphaneleri genellikle kendi float türleri için montaj seviyesi optimizasyonuna sahiptir.


0
2017-08-02 07:28