Float præcision

Tags:    c++

<< < 12 > >>
Hey,

jeg er igang med at udvikle et program der skal bruge variable med vanvittig præcision ( jo mere præcision, jo bedre faktisk ), og til det formål har jeg brugt double long. Det virker også godt et langt stykke hen ad vejen, men på et tidspunkt er det ikke præcist nok..

I det tilfælde kunne jeg så godt tænke mig noget med mere præcision, men kan man det? og hvordan?



Det tror jeg ikke umiddelbart du kan med en primitiv datatype. Der skal du nok finde et bibliotek der understøtter en "tal-klasse" eller lignende. Du kan prøve at lave noget med nogle ints som er "kædet" sammen.

Lad os sige det er meget små tal du har (under 0). Så kan man måske bruge 8 ints (indkaplet i en klasse f.eks.). Når man så lægger sammen kan man lægge de korrekte værdier oven i den korrekte int. Den sidste bit i sin int lægger man til den højere hvis den bliver sat.

Det var mine forslag håber det hjælper.



Som Søren skriver kan du ikke få større præcision i C++ end det long double giver.
Der findes en del biblioteker der tilbyder typer med højere præcision. De kaldes ofte "Arbitrary Precision library", som f.eks:
www.apfloat.org/apfloat/

Ellers må du i gang med at lave det i hånden, det er ikke helt let, men en god øvelse.



Indlæg senest redigeret d. 13.10.2009 22:39 af Bruger #4996
Der er ganske rigtigt tale om meget små tal..

Da det er til et hobby projekt, synes jeg det kunne være sjovt at lave det selv. Kender du en side der kan pege mig i den rigtige retning?

Så vidt jeg kan læse mig til på wiki'en er division et af de større problemer, men det skal jeg ikke bruge - hvis det gør nogen forskel :)

- Troels



Jeg har ikke en reference og har ikke prøvet at lave det selv.

Jeg ville lave det som en class med operatorer til at gøre arbejdet. Og jeg ville starte med at lave det med heltal og så udbygge til decimal tal bagefter.



Er så småt kommet igang med at bygge min class, men synes efterhånden at main filen er ved at bliver ret overskuelig..

Har set at andre deler et program over flere .cpp filer og så stadig har funktionaliteten fra alle filerne - how to do this ? :)



Du laver en .h fil med selve class'en:
class MyType
{
void Whatever();
....
};

Og laver en .cpp fil med alle funktionerne:
void MyType::Whatever()
{
...
}

Det er ret almindeligt at kalde disse filer MyType.h og MyType.cpp

I MyType.cpp og hoved .cpp filen (typisk main.cpp) inkluderer du så MyType.h

Og du inkluderer begge .cpp filer i projektet.



Ah, det er ser dejligt simpelt ud :D

Tusind tak for hjælpen !

Har dog enndu et lille spørgsmål..
Til at bygge min klasse har jeg tænkt mig at gøre brug af bitwise operators, men har opdaget noget jeg ikke forstår..

Fold kodeboks ind/udKode 

Producere output

128 512
1 4

Hvilket giver mening nok, idet a bliver opgraderet til en int for at kunne huse 512.

Men hvis jeg istedet for left-shift bruger right-shift får jeg output

128 32
1 4

.. og det er der jeg ikke forstår det længere!
Hvilken grund er der til det? 32 kan jo sagtens huses i en char - so why the upgrade?



Indlæg senest redigeret d. 20.10.2009 23:45 af Bruger #10853
idet a bliver opgraderet til en int for at kunne huse 512

Nej, det er ikke sådan det foregår, compileren vælger ikke type efter at de skal være store nok, den har nogle helt faste regler at vælge typer ud fra. Og 512 kunne godt være i en short.

Resultatet af en operation som (a << n) eller (a >> n) er en int, hvis a er en char, short eller int. Uanset om resultatet kan være i en char. Og (a << n) er en long hvis a er en long.

Størrelsen har ikke noget med værdien af a at gøre, kun med dens type. I dit simple eksempel kan compileren godt regne ud hvor mange bits den skal bruge til at gemme resultatet, men det kan den ikke altid, og du har ikke altid chance for at vide om den kan regne det ud.

Husk at sizeof bliver evalueret på compiletidspunktet, ikke mens programmet kører.



Okay, men jeg har blot brug at gemme de bit der kan være i char (altså hvor det giver nul hvis jeg (128 << 1)).

Vil den hurtigeste ( CPU mæssigt ) løsning så være
Fold kodeboks ind/udKode 

eller er der en anden løsnings metode der er bedre?

og som altid - tak for en fremragende( og hurtige ) hjælp :)



Indlæg senest redigeret d. 21.10.2009 00:41 af Bruger #10853
a = (( a << 1 ) & byte );


Du behøver ikke at maskere de bit væk (& byte) som du ikke skal bruge i ovenstående. a er en unsigned char, og kan (i normale tilfælde) kun gemme 8 bit, de øvrige bits bliver "automatisk" smidt væk.

Hvis du har:
unsigned char a = 128;
a = a << 1;

Vil der i sidste linje ske følgende:
a bliver "promoted" til en unsigned int, denne bliver shiftet 1 tak til venstre, og vil dermed indeholde 256. Men i din assignment (a = ...) vil den "midlertidige" int, blive trunkeret til en unsigned char igen, det sker ved at alt andet end de nederste 8 bit bliver smidt væk, og a vil ende med at være 0.

(I praksis er det muligt at compileren gør noget andet, men resultatet er det samme...)



<< < 12 > >>
t