-
71. Data: 2013-03-27 01:38:25
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: bartekltg <b...@g...com>
W dniu 2013-03-26 23:40, M.M. pisze:
> W dniu wtorek, 26 marca 2013 23:01:23 UTC+1 użytkownik bartekltg napisał:
>> W dniu 2013-03-26 12:25, M.M. pisze:
>>
>>> Niczego to nie zmienia. Logarytm tez mozna policzyc na mantysie o 2 bity
>>> dluzszej (np. na precyzji 66bitow) i wynik bylby dokladny.
>> :)
>> Szkolny przykład.
>> x=1/4;
>> x <- 4*x*(1-x).
>> Powinien wyjść cykl 1/4, 3/4, 1/4...
> Mnie chodziło jeszcze o coś innego, ale świetle tego, że procesory
> liczą zawsze tak samo, to już jest nieważne :)
>
>
>> Dla lepszego związku z tematem dodam, że dwa bity więcej
>> nie spowodują, że zawsze dostaniesz dobry wynik. Dwa
>> bity więcej oznaczają, że najczęściej dostaniesz poprawny
>> wynik.
> No tak, ale to jednak inny przykład i obliczenia pomimo że
> proste, to znacznie bardziej skomplikowane od tych, o jakie
> mnie chodziło. Jeśli mamy N liczb i każda z nich jest sumą
> całkowitych potęg dwójki, wszystkie są dodatnie, razem
> sumują się (dokładnie) do jedynki i mieszczą się w typie, to
> w wyniku poniższych operacji na tych liczbach:
> i = rand( 1 , N )
> j = rand( 1 , N )
> tmp = x[i] * 0.5;
> x[i] -= tmp;
> x[j] += tmp;
> Suma nie powinna odbiegać od jeden? Odpalam jeden tego
> typu program na dobę i po dobie obliczeń nie mam straty
> dokładności.
To czemu nie zrobiłeś tego na intach;>
Już daję kontrprzykład.
X ma dwa elementy.
Za każdym razem losujemy
i=1
j=2
Czyli za każdym razem połowa pierwszego elementu idzie do drugiego.
w k tym kroku
x[1] = 0.5^(k+1)
x[2] = 1 - 0.5^(k+1)
Przy odpowiednim sposobie zaokrąglania pojawi się +-epsylon.
Np jeśli mamy zaokrąglanie w dół, jest klapa.
Pewnie bez trudu zmontujesz przykład, gdzie liczby pozostają
podobnego rozmiaru, a ta jedynka wędruje w keirunku przecinka
i w końcu go mija.
Zaokrąglanie zaokrąglaniem, ale nieprawdą jest to:
>
>> Odpłynęliśmy równie daleko, mimo, że zarówno argument
>> naszego wyrażenia, jak i wynik były zapisywalne dokładnie.
> Hmmm, ale wszystkie pośrednie wyniki też były dokładne? Bo
> w przykładzie o jaki mnie chodzi, wszystkie pośrednie wyniki
> przynajmniej mogą być dokładne.
Nie, nie były dokładne. W najprostszym przypadku z przykładu
powyżej mamy ciągłe dodawanie małego elementu do ~jedynki
A, nie mówiąc już o tym, że sama procedura sumowania może
doprowadzić do błędów!
Dokładność 3 bity:
x= 10 000b + 1b +1b +1b +1b +1b +1b +1b +1b +1b +1b +1b +1b 1b +1b +1b +1b.
Wynik powinien byc 100 000b, a jest 10 000b
pzdr
bartekltg
-
72. Data: 2013-03-27 08:31:45
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "M.M." <m...@g...com>
W dniu środa, 27 marca 2013 01:38:25 UTC+1 użytkownik bartekltg napisał:
[...]
> A, nie mówiąc już o tym, że sama procedura sumowania może
> doprowadzić do błędów!
> Wynik powinien byc 100 000b, a jest 10 000b
Może rozmawiamy o innym przypadku? Ja mówię mniej/więcej o czymś takim:
#include <cstdlib>
#include <cstdio>
#include <ctime>
typedef double ftyp;
typedef const ftyp cftyp;
#define N (100)
#define M (1024)
#define K (1<<24)
#define L (8)
void init( ftyp v[N] ) {
for( int i=0 ; i<N ; i++ )
v[i] = 0;
for( int i=0 ; i<M ; i++ )
v[rand()%N] += 1.0 / M;
}
void compute( ftyp v[N] ) {
for( int i=0 ; i<K ; i++ ) {
const int s = rand() % N;
const int t = rand() % N;
ftyp d = 0;
for( int j=0 ; j<L ; j++ )
if( rand() % 1 )
d += 1.0 / ( 1<<(j+1) );
cftyp tmp = v[s] * d;
v[s] -= tmp;
v[t] += tmp;
}
}
void test( cftyp v[N] ) {
ftyp sum = 0;
for( int i=0 ; i<N ; i++ )
sum += v[i];
printf( "%0.20lf %s\n" , sum-1.0, sum==1.0?"true":"false" );
}
int main(int argc, char *argv[]) {
srand(time(NULL));
ftyp v[N];
init(v);
compute(v);
test(v);
return 0;
}
Wynik na kompie/kompilatorze przy którym akurat siedzę:
0.00000000000000000000 true
Pozdrawiam
-
73. Data: 2013-03-27 08:42:45
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: Tomasz Kaczanowski <kaczus@dowyciecia_poczta.onet.pl>
W dniu 2013-03-26 19:02, Adam Klobukowski pisze:
> On Tuesday, 26 March 2013 17:43:21 UTC+1, M.M. wrote:
>> W dniu wtorek, 26 marca 2013 14:48:52 UTC+1 użytkownik AK napisał:
>>
>>> Użytkownik "darekm" napisał:
>>
>>>> bo zachowuje wsteczną kompatybilność
>>
>>> 100% racji.
>>
>> No dobra, ale dlaczego to jest racja? Nie ma gwarancji dokładnego wyniku
>> na obliczeniach zmiennoprzecinkowych, czyli DOBRZE napisane programy
>> numeryczne powinny nadal działać, albo przynajmniej się kompilować,
>> na procesory ze lekko zmienioną dokładnością obliczeń.
>
> Nie. W przypadku obliczeń zmiennoprzecinkowych obowiązuje standard IEEE i wszystkie
szeroko używane procesory się do niego stosują. Ten standard określa jak procesor ma
obliczać i o ile się mylić :)
standard IEEE nie określa czy wyniki pośrednie mają być zwracane do
pamięci i potem pobierane. Dodatkowo tryb rozszerzony w standardzie IEEE
to z tego co pamiętam i 80 i 128 bitów - w zależności od procesora a
liczbach o większej bitowości zazwyczaj przeprowadzane są obliczenia.
--
Kaczus
http://kaczus.republika.pl
-
74. Data: 2013-03-27 08:47:46
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: Tomasz Kaczanowski <kaczus@dowyciecia_poczta.onet.pl>
W dniu 2013-03-26 22:29, M.M. pisze:
> W dniu wtorek, 26 marca 2013 22:01:28 UTC+1 użytkownik Adam Klobukowski napisał:
>
>> Standard definiuje miedzy innymi typy danych (np 32, 64, 80 bit float), i w
>> jego zakresie nie da się zmienić dokładności.
> Dla mnie z tego nic nie wynika. Nie wiem co znaczy "zmienić dokładność".
>
> Jeśli typ składa się z iluś tam bitów, jedyną sensowną dokładnością jaką
> jestem sobie w stanie wyobrazić, jest dokładność co do najmniej znaczącego
> bitu. Jeśli liczba jest sumą całkowitych potęg dwójki i mieści się w zakresie
> typu, to nie ma żadnego ważnego powodu aby obliczenia nie były przeprowadzone
> dokładnie.
Podstawowy powód - wielkość liczb - jeśli różnica jest duża, to będą
duże róznice przy dodawaniu.
--
Kaczus
http://kaczus.republika.pl
-
75. Data: 2013-03-27 08:54:12
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "AK" <n...@n...com>
Użytkownik "Adam Klobukowski" <a...@g...com> napisał:
> http://en.wikipedia.org/wiki/IEEE_floating_point
W standardzie IEEE piszesz programy ?
AK
-
76. Data: 2013-03-27 08:55:41
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "AK" <n...@n...com>
Użytkownik "M.M." <m...@g...com> napisał:
> Mnie chodziło jeszcze o coś innego, ale świetle tego, że procesory
> liczą zawsze tak samo
Nie ! NIE licza tak samo !.
Nie w koprocesorach pisze sie programy.
AK
-
77. Data: 2013-03-27 09:42:23
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "M.M." <m...@g...com>
W dniu środa, 27 marca 2013 08:31:45 UTC+1 użytkownik M.M. napisał:
> W dniu środa, 27 marca 2013 01:38:25 UTC+1 użytkownik bartekltg napisał:
>
> [...]
>
> > A, nie mówiąc już o tym, że sama procedura sumowania może
>
> > doprowadzić do błędów!
>
> > Wynik powinien byc 100 000b, a jest 10 000b
>
> Może rozmawiamy o innym przypadku? Ja mówię mniej/więcej o czymś takim:
[...]
Ten przykład to był babol. On też nie spełnia tego o czym mówię i
maił błąd. Ten zdaje się już jest dobry:
#include <cstdlib>
#include <cstdio>
#include <ctime>
typedef double ftyp;
typedef const ftyp cftyp;
#define N (100)
#define M (1<<10)
#define K (1000000)
void init( ftyp v[N] ) {
for( int i=0 ; i<N ; i++ )
v[i] = 0;
for( int i=0 ; i<M ; i++ )
v[rand()%N] += 1.0 / M;
}
void compute( ftyp v[N] ) {
for( int i=0 ; i<K ; i++ ) {
int s,t;
double tmp;
do {
s = rand() % N;
t = rand() % N;
tmp = 1.0 / M * (rand()%M);
} while( s==t || tmp > v[s] );
v[s] -= tmp;
v[t] += tmp;
}
}
void test( cftyp v[N] ) {
ftyp sum = 0;
for( int i=0 ; i<N ; i++ )
sum += v[i];
printf( "%0.20lf %s\n" , sum-1.0, sum==1.0?"true":"false" );
}
int main(int argc, char *argv[]) {
srand( 33 );
ftyp v[N];
init(v);
compute(v);
test(v);
return 0;
}
-
78. Data: 2013-03-27 09:47:33
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "M.M." <m...@g...com>
W dniu środa, 27 marca 2013 08:55:41 UTC+1 użytkownik AK napisał:
> Nie ! NIE licza tak samo !.
> Nie w koprocesorach pisze sie programy.
Albo liczą zawsze tak samo (poza patologią), albo nie. To
czy program napisze się na kartce papieru, w asemblerze, czy w C++
nie ma na to wpływu.
Pozdrawiam
-
79. Data: 2013-03-27 10:10:29
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: Tomasz Kaczanowski <kaczus@dowyciecia_poczta.onet.pl>
W dniu 2013-03-27 09:47, M.M. pisze:
> W dniu środa, 27 marca 2013 08:55:41 UTC+1 użytkownik AK napisał:
>> Nie ! NIE licza tak samo !.
>> Nie w koprocesorach pisze sie programy.
> Albo liczą zawsze tak samo (poza patologią), albo nie.
Nie liczą, może być inna reprezentacja chocby rejestrow wewnetrznych,
dodatkowo obliczenia moga byc wykonane bez konwersji wyników pośrednich,
albo z konwersją, na typ wynikowy.
--
Kaczus
http://kaczus.republika.pl
-
80. Data: 2013-03-27 10:25:49
Temat: Re: Nowoczesne procesory - jak to z nimi jest?
Od: "M.M." <m...@g...com>
W dniu środa, 27 marca 2013 10:10:29 UTC+1 użytkownik Tomasz Kaczanowski napisał:
> Nie licz�, mo�e by� inna reprezentacja chocby rejestrow wewnetrznych,
> dodatkowo obliczenia moga byc wykonane bez konwersji wynik�w po�rednich,
> albo z konwersjďż˝, na typ wynikowy.
Ja nie wiem, a ta dyskusja jeszcze wiecej mi namieszala niz wyjasnila. Prawie
zawsze staram sie napisac program tak, aby działał tym dokładniej, im
dokładniejsze są wyniki obliczeń. Czyli zakładam pewną niedokładność. Jak
zakładam bliżej nieokreśloną dokładność, to jest mi obojętne czy procesory
liczą identycznie, tak samo, czy zupełnie inaczej. Niemniej kilka razy
napisałem programy który zakłada dokładne wyniki obliczeń na zmiennoprzecinkowych i
te programy działają poprawie, a nawet są pewne
korzyści z tego założenia.
Pozdrawiam