Ek het 'n program wat loop op twee verwerkers, waarvan een nie 'n drywende punt ondersteuning. So, ek moet verrig drywende punt berekeninge met behulp van vaste punt in daardie verwerker. Vir dié doel, sal ek met 'n drywende punt nydigheid biblioteek. Ek moet eers pak die tekens, mantissas en eksponente van drywende punt nommers op die verwerker wat nie ondersteun drywende punt. So, my vraag is hoe kan ek die teken, MANTISSA en eksponent van 'n enkele presisie drywende punt nommer. Na aanleiding van die formaat van hierdie figuur, Dit is wat Ive tot dusver gedoen het, maar behalwe teken nie MANTISSA en eksponent korrek is. Ek dink, Im mis iets. gevra 28 Maart 13 aan 15:00 I39m veronderstelling IEEE 754 32 bit binêre. Is jy bewus van die volgende kwessies (1) Die eksponent is biassed, deur die toevoeging van 127 om die werklike eksponent. (2) Alle behalwe baie klein dryf is genormaliseer, en die voorste 1 bietjie van 'n genormaliseerde float MANTISSA is nie gestoor. â € Patricia Shanahan 28 Maart 13 by 17:05 There39s geen wet wat sê jy moet net gebruik dinge vir wat hulle oorspronklik geskep vir. Anders sal die eerste vliegtuig wouldn39t gebruik stukkies fiets. quotGenerallyquot ongedefinieerd Wat van daardie geleenthede waar dit gedefinieer word, of wanneer you39re tevrede met die gedrag van 'n gegewe platform / situasie uitvoering maak Alex 28 Februarie 14 by 11:29 Alex Daar is eintlik 'n wet wat sê jy kan net 'n paar dinge en nie die ander nie in C. It39s genoem die quotISO / IEC 9899: 2011 specificationquot, omgangstaal bekend as die quotC taal standardquot. En as dit vir jou vertel dat wat you39re doen ongedefinieerd wat beteken dat jy kan enigiets terug te kry. Op 'n dag dit kan werk, die volgende kon jy die verkeerde gevolg gee en nog die volgende dag dit kan net crash. That39s wat quotundefinedquot beteken. â € Voo 24 Februarie by 19:08 Hierdie metode misluk wanneer 1) float nie IEEE 754 32 bit binêre (nie so skaars) 2) ongetekende is 16-bit (algemeen in ingebed wêreld) 3) endian van unsigned47float stem nie ooreen nie. (Skaars). 4) Wiskundige interpretasie gebruik word vir exponent47mantissa as hierdie antwoord toon die bevooroordeeld eksponent en die onvolledige significand / MANTISSA. â € chux 5 Maart by 17:34 Vind uit die formaat van die drywende punt nommers wat op die CPU wat direk ondersteun drywende punt en breek dit af in daardie dele. Die mees algemene formaat is IEEE-754. Alternatiewelik kan jy die dele met behulp van 'n paar spesiale funksies (dubbel frexp (dubbel waarde, int exp) en dubbel ldexp (dubbel x, int exp)), soos uiteengesit in hierdie antwoord kry. My raad is om te hou om te heers 0 en nie oordoen watter standaard biblioteke reeds doen, as dit is genoeg. Kyk na math. h (cmath in standaard C) en funksies frexp, frexpf, frexpl, wat 'n drywende punt waarde (dubbel, vlot, of 'n lang dubbel) breek in sy significand en eksponent deel. Om die teken van die significand jy kan signbit gebruik, ook in math. h / cmath, of copysign (slegs C11) te onttrek. Sommige alternatiewe, met skraler verskillende semantiek, is modf en ilogb / scalbn, beskikbaar in C11 en. cppreference / w / CPP / numeriese / wiskunde / logb hulle vergelyk, maar ek didnt vind in die dokumentasie hoe al hierdie funksies op te tree met / - inf en Nans. Ten slotte, as jy regtig wil om bitmasks (bv jy dringend nodig het om die presiese stukkies weet, en jou program kan verskillende Nans met verskillende voorstellings, en jy dit nie vertrou bogenoemde funksies), ten minste maak alles platform-onafhanklike deur gebruik te maak van die gebruik makros in float. h / cfloat. antwoord 26 Oktober 13 aan 16:12 Julle amp ing die verkeerde stukkies. Ek dink jy wil: Onthou, wanneer jy amp. jy Nulstellen uit stukkies wat jy hoef te stel. So in hierdie geval, jy wil nul uit die teken bietjie wanneer jy die eksponent kry, en jy wil nul uit die teken bietjie en die eksponent wanneer jy die MANTISSA kry. Let daarop dat die maskers kom direk van jou foto. Dus, sal die eksponent masker lyk: 0 11111111 00000000000000000000000 en die MANTISSA masker sal lyk: 0 00000000 11111111111111111111111 antwoord 28 Maart 13 aan 15:07 Ek het nog don39t korrekte resultate te kry. â € MetallicPriest 28 Maart 13 by 15:10 MetallicPriest Probeer nou, ek het die verkeerde maskers die eerste keer. â € Xymostech 28 Maart 13 by 15:12 Wat oor die sogenaamde verborge bietjie Ek don39t sien iemand sit dit: m 0x00800000. Let daarop dat die nommer moet nagegaan word vir spesiale waardes (denormals, NaN, oneindighede) eerste, aangesien hierdie vereis verskillende behandeling. â € Rudy Velthuis 29 Maart 13 by 22: 16Floating Point Thomas Finley, April 2000 Inhoud en Inleiding Hierdie dokument verduidelik die IEEE 754 swaai-punt standaard. Dit verduidelik die binêre voorstelling van hierdie getalle, hoe om te skakel na desimaal uit drywende punt, hoe om te sit van drywende punt om desimaal bespreek spesiale gevalle in drywende punt, en uiteindelik eindig met 'n paar C-kode vir kinders begrip van drywende punt te bevorder. Hierdie dokument dek nie bedrywighede met drywende punt getalle. Ek het hierdie dokument so dat as jy weet hoe om voor te stel, kan jy die artikel verteenwoordiging slaan, en as jy weet hoe om te skakel na desimaal uit enkele presisie, kan jy daardie artikel slaan, en as jy weet hoe om te skakel na enkele presisie uit desimale, kan jy daardie artikel slaan. Verteenwoordiging In die eerste plek weet dat binêre getalle kan hê, as jy sal my gesê so 'n desimale punt vergewe. Dit werk min of meer dieselfde wyse as wat die desimale punt doen met desimale getalle. Byvoorbeeld, die desimale 22,589 bloot 22 en 510 -1 810 -2 910 -3. Net so is die binêre getal 101,001 is eenvoudig 12 2 02 1 12 0 02 -1 02 -2 12 -3. of eerder net 2 2 2 0 2 -3 (hierdie spesifieke aantal werk uit te wees 9,125, as dit jou denke help). Tweedens, weet dat binêre getalle, soos desimale getalle, kan in wetenskaplike notasie. Bv Die desimale 923,52 kan soos volg voorgestel word 9,2352 10 2. Net so, binêre getalle uitgedruk kan word dat die pad so goed. Sê ons het die binêre getal 101011.101 (wat is 43,625). Dit sou voorgestel word deur wetenskaplike notasie as 1.01011101 2 5. Nou dat Im seker die begrip is volmaak nie, kan ek uiteindelik kry in verteenwoordiging. Die enkele presisie drywende punt eenheid is 'n pakkie van 32 stukkies, verdeel in drie afdelings 'n bietjie, agt stukkies, en drie en twintig stukkies, in daardie volgorde. Ek sal gebruik maak van die voorheen genoem binêre getal 1.01011101 2 5 maak om te illustreer hoe 'n mens 'n binêre getal in wetenskaplike notasie sou neem en dit op drywende punt notasie. As ons net sit van Hex binêre, 0x64 is 0110 0100, wat dieselfde resultaat as die 011001 bo opgelewer. Hierdie metode is baie vinniger. In elk geval Ons neem die getalle wat ons gekry het, en hulle verteenwoordig as 0,011001, plaas hulle in die volgorde wat ons hulle verkry. Plaas in volgorde met ons binêre voorstelling van 329, kry ons 101.001.001,011001. In ons binêre wetenskaplike notasie, dit is 1,01001001011001 2 8. Ons gebruik dan wat ons weet oor hoe enkele presisie getalle verteenwoordig om hierdie proses te voltooi. Die teken is positief, dus is die veld teken is 0. Die eksponent is 8. 8 127 135, sodat die veld eksponent is 10000111. Die MANTISSA is bloot 01001001011001 (onthou die geïmpliseer 1 van die MANTISSA beteken dat ons dit nie sluit die voorste 1) plus egter baie 0e ons moet voeg na die regterkant na daardie binêre getal 23 stukkies lank maak. Sedert een van die huiswerkprobleme behels hierdie verteenwoordig as Hex, sal ek klaar met 'n blok nommer. Dan breek ons dit in vier bietjie stukke (sedert elke heksadesimale syfer is gelykstaande aan 4 stukkies) en dan sit elke vier bietjie hoeveelheid in die ooreenstemmende heksadesimale syfer. So, in heksadesimaal, hierdie nommer is 0x43A4B200. Spesiale Nommers Soms is die rekenaar voel 'n behoefte gevolg uit te steek van 'n berekening wat weerspieël dat sommige fout gemaak. Miskien is die grootte van die resultaat van 'n berekening was groter of kleiner as hierdie formaat blyk te wees om te ondersteun. Miskien probeer jy om te verdeel deur nul. Miskien is jy probeer om verteenwoordig nul Hoe word 'n ooreenkoms met hierdie kwessies Die antwoord is dat daar spesiale gevalle van drywende punt getalle, spesifiek wanneer die veld eksponent is al 1 stukkies (255) of al 0 stukkies (0). Denormalized Nommers As jy 'n eksponent veld dis al nul stukkies, dit is whats genoem denormalized nommer. Met die veld eksponent gelyk aan nul, sou jy dink dat die werklike eksponent -127 sou wees, sodat hierdie nommer die vorm van 1.MANTISSA 2 -127 soos hierbo beskryf sou neem, maar dit beteken nie. In plaas daarvan, is dit 0.MANTISSA 2 -126. Let daarop dat die eksponent is nie meer die waarde van die veld eksponent minus 127. Dit is eenvoudig -126. Let ook op dat ons nie meer 'n stilswyende 'n bietjie vir die MANTISSA sluit. As 'n voorbeeld, neem die drywende punt getal verteenwoordig as 0x80280000. In die eerste plek te sit hierdie binêre. Ons teken bietjie is 1, sodat hierdie nommer is negatief. Ons eksponent is 0, sodat ons weet dit is 'n denormalized nommer. Ons MANTISSA is 0101, wat 'n ware MANTISSA van 0,0101 onthou ons nie sluit wat voorheen 'n stilswyende 'n bietjie vir 'n eksponent van nul weerspieël. So, dit beteken ons het 'n aantal -0,0101 2 2 -126 -0,3125 10 2 -126 -1,25 10 2 -128. Zero Jy kan dink nul as net nog 'n denormalized nommer. Zero word verteenwoordig deur 'n eksponent van nul en 'n MANTISSA van nul. Van ons begrip van denormalized getalle, dit vertaal in 02 -126 0. Hierdie teken bietjie kan óf positief (0) of negatief (1), wat lei tot 'n positiewe of negatiewe zero. Dit nie die geval is maak baie sin wiskundig, maar dit word toegelaat nie. Infinity Net soos die geval van alle nul stukkies in die veld eksponent is 'n spesiale geval, so is die geval van alle mens stukkies. As die veld eksponent is al kinders en die MANTISSA is al nulle, dan is hierdie getal is 'n oneindig. Daar kan óf positief of negatief oneindighede afhangende van die teken bietjie. Byvoorbeeld, 0x7F800000 positief oneindig, en 0xFF800000 negatief oneindig. NaN (nie 'n nommer) Hierdie spesiale hoeveelhede 'n eksponent gebied van 255 (almal een stukkies) soos oneindigheid, maar verskil van die voorstelling van die oneindigheid in die MANTISSA bevat 'n paar een stukkies. Dit maak nie saak waar hulle is of hoe baie van hulle daar is, net so lank as wat daar is 'n paar. Die teken bietjie blykbaar geen invloed op hierdie te hê. Voorbeelde van hierdie spesiale hoeveelheid sluit 0x7FFFFFFF, 0xFF81ABD0, 0x7FAA12F9, en soforth. Opsomming van spesiale gevalle 'n Opsomming van spesiale gevalle word in die tabel hieronder. Dit is min of meer 'n afskrif van die tabel op bladsy 301 van die tweede uitgawe van Computer Organization and Design, die Hardware sagteware koppelvlak deur Patterson en Hennessy, die handboek vir Rekenaarwetenskap 104 in die lente 2000 semester. Selfs al is net enkele presisie is gedek in die bogenoemde teks, ek sluit dubbele presisie ter wille van volledigheid. Wanneer, Waar, en Waar Nie wanneer jy bedrywighede soos 0/0 of af te trek oneindigheid van oneindigheid (of 'n ander dubbelsinnige berekening) het, sal jy NaN kry. Wanneer julle 'n skeiding van 'n aantal deur nul is, sal jy 'n oneindigheid te kry. Maar, rekeningkunde vir hierdie spesiale operasies neem 'n paar ekstra poging aan die kant van die ontwerper, en kan lei tot stadiger bedrywighede as meer transistors gebruik word in chip ontwerp. Om hierdie rede soms CPUs nie verantwoordelik vir hierdie bedrywighede, en in plaas genereer 'n uitsondering nie. Byvoorbeeld, wanneer ek probeer om te verdeel deur nul of doen bedrywighede met oneindigheid, my rekenaar genereer uitsonderings en weier om die aksie te voltooi (my rekenaar het 'n G3-verwerker, of MPC750). Helper sagteware As jy belangstel in verdere ondersoek, ek sluit twee programme waarvoor ek verskaf die C-kode wat jy kan hardloop om 'n beter begrip van hoe swaai punt werke, en ook om jou werk na te gaan op verskeie opdragte te kry. Hex 2 Float Hierdie program aanvaar as toevoer 'n heksadesimale hoeveelheid en lees dit as rou data in die veranderlike theFloat. Die program uitgange dan die heksadesimale voorstelling van die data in theFloat (herhaling van die insette), en druk saam met dit die drywende punt hoeveelheid wat dit verteenwoordig. Ek wys hier 'n voorbeeld loop van die program. Let op die spesiale geval swaai punt hoeveelhede (0, oneindig, en nie 'n paar). Vir die denormalized maar nie-nul getalle, sal hierdie program vertoon nul selfs al is die getal is nie regtig nul. As jy wil om hierdie probleem te kry, vervang die f in die opmaak string van die printf funksie met e, wat die getal sal deplay groot presisie met wetenskaplike notasie. Ek het dit nie as 'n e omdat ek vind wetenskaplike notasie uiters irriterende. Dryf 2 Hex Dit is 'n effense wysiging van die Hex 2 Float program. Die uitsondering is dit lui in 'n drywende punt nommer. Net soos en uitgange die heksadesimale vorm plus die swaai punt nommer. Weereens ek sluit 'n monster loop van hierdie program, wat bevestig dat die resultate van die voorbeeld probleme wat ek vroeër gedek in hierdie teks, saam met 'n paar ander eenvoudige gevalle. Let op die heksadesimale voorstelling van 0.2. En dis die einde van die hoofstuk. Thomas Finley 2000You kan hierdie artikel as óf 'n Word97 of RTF-lêer af te laai. Dit artikels van toepassing op alle weergawes van Microsoft Excel vir Windows. Hierdie artikel is geskryf deur Chip Pearson, 27-Oktober-1998. Kopiereg, 1998, 1999, Charles H. Pearson Hierdie artikel beskryf die redes waarom jy rekenkundige foute kan ervaar in Microsoft Excel97. Inhoudsopgawe: Werklike en uitgestal Waardes wisselpuntgetalle Werkkaart funksies Afronding IEEE swaai Point Standard Hierdie artikel veronderstel dat jy vertroud is met die volgende: Die Excel Aansoek Visual Basic for Applications (VBA) programmeringskonsepte die binêre stelsels van getalle Daar mag tye wees dat die waarde wat jy sien op 'n Excel-werkblad is nie gelyk aan die waarde wat jy glo dat dit behoort te wees. Daar is oor die algemeen twee moontlike oorsake van hierdie probleem. Die eerste is dat die getalle nie vertoon word om hul volle waardes. Die tweede is 'n rekenaar ontwerp kwessie. Nie een van die twee is quotbugsquot of probleme met die ontwerp van Microsoft Excel of Windows. Excel winkels getalle anders wat u mag hê hulle geformateer vertoon op die werkkaart. Onder normale omstandighede, Excel winkels numeriese waardes as quotDouble Precision wisseltrofee Pointquot getalle, of quotDoublesquot vir 'n kort. Dit is 8-byte veranderlikes wat getalle akkuraat tot ongeveer 15 desimale plekke kan stoor. Jy kan net twee desimale plekke vertoon op die werkblad te hê, maar die onderliggende waarde het die volle 15 desimale plekke. Die tweede probleem spruit uit die feit dat 'n rekenaar, 'n rekenaar, kan nie die meeste fraksionele getalle te stoor met 'n totale akkuraatheid. Rekenaars, in die algemeen, gebruik die IEEE (Instituut vir Elektriese en Elektroniese Ingenieurs) standaard vir drywende punt getalle. Hierdie standaard bied 'n manier om fraksionele getalle te stoor in die beperkte ruimte van 'n 8-byte nommer. Natuurlik, vir die meeste nommers, sommige benadering moet gedoen word. Hierdie artikel beskryf en verduidelik die oorsake vir foute wat as gevolg van een van die hierbo beskryf oorsake is: die vertoon formaat nommer en die interne foute wat verband hou met drywende punt getalle. Werklike en uitgestal Waardes Onder normale omstandighede, Excel altyd winkels en manipuleer nommers as 8-byte quotDouble Precision wisseltrofee Pointquot getalle, of quotDoublesquot. Blink interne stoor van die getal is nie geraak word deur die manier waarop jy kan kies om 'n aantal formaat vir vertoning. Byvoorbeeld, as 'n sel bevat die formule 1/3. Excel behandel altyd hierdie waarde as 0.3333133, ongeag hoeveel desimale plekke wat jy kies om te vertoon op die werkkaart. Selfs as jy kies om die waarde so eenvoudig quot0.3quot vertoon, Excel behou steeds die volledige getal as die waarde van die sel. Dit kan situasies waarin dit kan voorkom asof Excel maak 'n fout in die berekening, wanneer dit werklik is nie veroorsaak. Byvoorbeeld, veronderstel ons het die formule 1/3 in elk van die drie selle A1: A3. Opmaak hierdie sel vir een desimale punt sou quot0.3quot in elke sel aan te toon. hierdie drie selle toe te voeg saam met die som funksie sal die resultaat 1.0 gee. Maar 0.3 0.3 0.3 gelyk 0.9 nie 1.0, reg Die resultaat lyk verkeerd te wees. Natuurlik, dit is nie. Ongeag van hoe jy die selle formaat vir vertoning, Excel gebruik die onderliggende waarde wanneer berekenings. In die voorbeeld, is jy nie regtig die toevoeging van 0,3 0,3 0,3. maar eerder ,333333333333333 ,333333333333333 ,333333333333333. waarvan die som (byna) 1.0. Excel doen bied 'n opsie genaamd quotPrecision Soos Displayedquot, wat jy kan in staat stel om uit blad C alculate op die Options dialoog (kieslys). As hierdie opsie geaktiveer dwing Excel om die vertoon waardes gebruik in sy berekeninge, eerder as die onderliggende getalle. Met hierdie opsie geaktiveer is, die voorbeeld hierbo inderdaad som tot 0.9. Jy moet baie versigtig wees wanneer die gebruik van hierdie opsie, egter. Sodra geaktiveer is, is al presisie verloor, en kan nie herwin. Alle selle word bereken op grond van die vertoon waarde. Hierdie opsie is van toepassing op die hele werkboek, nie aan 'n spesifieke sel of reeks selle. Wisselpuntgetalle Excel, soos byna elke ander rekenaarprogram, maak gebruik van die IEEE standaard vir Double Precision wisselpuntgetalle. Hierdie standaard is beskryf in detail, na die bietjie vlak, in 'n latere afdeling van hierdie artikel. Ons kan dit veralgemeen, al is, om te beskryf hoe Excel winkels fraksionele getalle. Net soos rekenaars stoor heelgetalle as binêre getalle, slaan hulle fraksionele getalle as binêre breuke. Rekenaars slaan 'n heelgetal (heelgetal) waarde as (x1 x2 x4 x8 x16 ens) waar x die toestand van die bietjie. As die bietjie op, x1. As die bietjie af, x0. In hierdie notasie kan enige heelgetal presies gestoor word. Byvoorbeeld, is die nommer 13 wat gestoor word in binêre as 1101 wat aandui, lees van links na regs, 18 14 02 11 13 Fraksionele nommers gestoor in 'n soortgelyke wyse. In die binêre stelsel, is fraksionele getalle gestoor as die som van 'n reeks van breuke: (x1 / 2 x1 / 4 x1 / 8 x1 / 16 ens) waar x die toestand van die bietjie. As die bietjie op, x1. As die bietjie af, x0. In teenstelling met heelgetalle egter nie elke fraksionele waarde kan presies akkuraat gestoor. Byvoorbeeld, is dit onmoontlik om die getal te stoor 10/01 0.1 in tweeledige vorm. 'N Noue benadering is (02/01 04/01 08/01 11/16 11/32 ens). Rekenaars voer hierdie aksie om die ekwivalent van 15 desimale plekke. Selfs met hierdie akkuraatheid, is baie getalle verteenwoordig as 'n benadering van hul quottruequot of quotanalyticquot waarde. Byvoorbeeld, is dit onmoontlik om akkuraat te beskryf die aantal 10/01 in 8-byte (of 'n onbepaalde) binêre notasie. Drywende punt getalle kan baie naby aan wat dat die getal kom, maar daar sal altyd 'n baie klein fout wees. Dit is belangrik om daarop te let dat hierdie foute en beperkings op fraksionele getalle is nie regtig foute nie. Of is hulle quotbugsquot in die programme. Dit is goed bekend en goed gedokumenteer beperkinge van die drywende punt rekenkundige stelsels in byna elke pakket en hardeware toestel. Werkkaart funksies Afronding Excel bied jou met 'n paar funksies te hanteer afronding. Hierdie funksies word hieronder gelys. INT MROUND ROUND ROUNDDOWN ROUNDUP TRUNC N Nota: Die MROUND funksie maak deel uit van die analise ToolPak Voeg-in vir Excel. Jy moet hierdie pakket om hierdie funksies te gebruik geïnstalleer het. Om die ATP te installeer, gaan na die kieslys te kies Invoegtoepassingen. en plaas 'n tjek langs die analise ToolPak item. Sien die on-line help vir meer inligting oor hierdie funksies. IEEE swaai Point Standard Die artikel beskryf die interne formaat van 64-bit dubbele presisie drywende punt veranderlikes. Die uitleg van 'n dubbele is soos volg: Die grootte van 'n float is platform-afhanklike, hoewel 'n maksimum van 1.8e308 met 'n akkuraatheid van ongeveer 14 desimale syfers is 'n algemene waarde (die 64 bit IEEE formaat). Drywende punt presisie drywende punt getalle het 'n beperkte akkuraatheid. Alhoewel dit hang af van die stelsel, PHP gebruik tipies die IEEE 754 dubbel presisie-formaat, wat 'n maksimum relatiewe fout as gevolg van afronding in die einde van 1.11e-16 sal gee. Nie ELEMENTARY rekenkundige operasies mag groter foute te gee, en, natuurlik, moet fout voortplanting ag geneem word wanneer 'n paar operasies saamgestel. Daarbenewens rasionale getalle wat presies representeerbaar as drywende punt getalle in basis 10, soos 0.1 of 0.7 is. het nie 'n presiese verteenwoordiging as drywende punt getalle in basis 2, wat intern gebruik word, maak nie saak van die grootte van die MANTISSA. Dus, kan hulle nie omskep word in hul interne binêre eweknieë sonder 'n klein verlies aan akkuraatheid. Dit kan lei tot verwarrende resultate: byvoorbeeld, sal vloer ((0.10.7) 10) gewoonlik terug 7 in plaas van die verwagte 8. aangesien die interne verteenwoordiging iets soos 7,9999999999999991118 sal wees. . So nooit vertrou swaai aantal resultate na die laaste syfer, en moenie drywende punt getalle nie vergelyk direk vir gelykheid. As hoër akkuraatheid nodig is, die arbitrêre presisie wiskunde funksies en GMP funksies is beskikbaar. Vir 'n quotsimplequot verduideliking, sien die raquo drywende punt gids that039s ook getiteld quotWhy hoef my getalle voeg upquot omskakeling te dryf Vir meer inligting oor die omskakeling string s te dryf. sien String omskakeling na getalle. Vir waardes van ander tipes, is die omskakeling deur die omskakeling van die waarde eers heelgetal is en dan om te dryf. Sien Omskakeling na heelgetal vir meer inligting. Vanaf PHP 5, is 'n kennisgewing gegooi as 'n voorwerp is omskep om te dryf. Vergelyk dryf Soos in die waarskuwing bo, toets drywende punt waardes vir gelykheid is problematies, as gevolg van die manier waarop hulle intern verteenwoordig. Daar is egter maniere om vergelykings van drywende punt waardes wat werk om hierdie beperkings te maak. Om swaai punt waardes op die relatiewe fout toets vir gelykheid, 'n bogrens as gevolg van afronding gebruik word. Hierdie waarde staan bekend as die masjien Epsilon, of eenheid roundoff, en is die kleinste aanvaarbare verskil in berekeninge. A en B is gelyk aan 5 syfers van presisie. ltphp n 1.23456789 b 1.23456780 epsilon 0,00001 as (ABS (a - b) Dit epsilon) eggo ware GT NaN Sommige numeriese bedrywighede kan lei tot 'n waarde verteenwoordig deur die konstante NAN. Hierdie resultaat verteenwoordig 'n ongedefinieerde of onvoorstelbare waarde in swaai-punt berekeninge. Enige los of streng vergelykings van hierdie waarde teenoor enige ander waarde, insluitend homself, sal weens ONWAAR het. Omdat NAN verteenwoordig 'n aantal van verskillende waardes, moet NAN nie vergelyk word met ander waardes, insluitend homself, en in plaas moet nagegaan word vir die gebruik van | isNaN (). Notes contributives 30 notas net 'n opmerking oor iets wat die drywende punt presisie insetsel, wat lui: Dit is verwant aan. 0,3333333. Terwyl die skrywer waarskynlik weet wat hulle praat, die verlies van presisie het niks te doen met desimale notasie, dit het te doen met verteenwoordiging as 'n swaai-punt binêre in 'n beperkte register, soos terwyl 0,8 eindig in desimale, dit is die herhaling van ,110011001100. in binêre, wat kapt. 0.1 en 0.7 is ook nie-eindig in binêre, sodat hulle ook afgekapte, en die som van hierdie afgekapte getalle nie optel na die afgeknotte binêre voorstelling van 0.8 (wat is die rede waarom (vloer) (0,810) lewer 'n ander, meer intuïtief, gevolg). Maar sedert 2 is 'n faktor van 10, 'n getal wat eindig in binêre ook beëindig in desimale. Algemene rekenaar wenk: As jy die dop van geld, doen jouself en jou gebruikers die guns van die hantering van alles intern in sent en doen soveel wiskunde as wat jy kan in heelgetalle. Store waardes in sent indien enigsins moontlik. Optel en aftrek in sent. By elke operasie wat wii betrek dryf, vra jouself wat sal gebeur in die werklike wêreld as ek kry 'n fraksie van 'n sent hier en as die antwoord is dat hierdie aksie 'n transaksie in heelgetal sent sal genereer, moenie probeer om fiktiewe fraksionele akkuraatheid dra wat sal net dinge skroef later. ltphp binarydata32 pak (H. 00000000) float32 pak (f. binarydata32) // 0.0 binarydata64 pak (H. 0000000000000000) float64 pak (d. binarydata64) // 0.0 GT ek 0 beide vir 32-bit en 64-bis getalle. Maar, please dont gebruik jou eie funksies te omskep van float om binêre en omgekeerd. Herhaling prestasie in PHP is verskriklik. Die gebruik van Pack / pak jy verwerkers enkodering, wat altyd korrek gebruik. In C kan jy toegang tot die dieselfde 32/64 data as óf float / dubbel of 32/64 bis integriteit. Geen doelskoppe. Om binêre encoding kry: ltphp float32 pak (. F 5300231) binarydata32 pak (H. float32) // 0EC0A14A float64 pak (. D 5300231) binarydata64 pak (H. float64) // 000000C001385441 GT En my voorbeeld van 'n half jaar gelede: ltphp binarydata32 pak (H. 0EC0A14A) float32 pak (f. binarydata32) // 5300231 binarydata64 pak (H. 000000C001385441) float64 pak (d. binarydata64) // 5300231 GT en asseblief omgee die Groot en Klein endian seuns. ID graag daarop wys 'n kenmerk van PHPs drywende punt ondersteuning wat duidelik isnt gemaak oral hier, en was besig om my mal. Hierdie toets (waar vardump sê dat a0.1 en b0.1) indien (agtb) eggo blah sal misluk in sommige gevalle as gevolg van verborge presisie (standaard C probleem, wat PHP dokumente maak geen melding gemaak van, so ek aanvaar hulle ontslae geraak daarvan). Ek moet daarop wys dat ek aanvanklik gedink dit was 'n probleem met die dryf gestoor as snare, sodat ek hulle gedwing om te dryf en hulle nog didnt behoorlik te evalueer (waarskynlik 2 verskillende probleme daar). Om vas te stel, moes ek hierdie verskriklike kludge (die gelykwaardig van elk geval) te doen: As (ronde (a, 3) gtround (b, 3)) eggo blah dit werk. Dit is duidelik dat alhoewel vardump sê die veranderlikes is identies, en hulle moet identies nie (begin by 0,01 en bygevoeg 0,001 herhaaldelik), theyre. Theres 'n paar verborge presisie daar buite wat besig was om my te skeur my hare uit. Miskien is dit moet die dokumentasie In sommige gevalle wil jy dalk die maksimum waarde vir 'n float kry sonder om INF bygevoeg. vardump (1.8e308) sal gewoonlik wys: float (INF) Ek het 'n klein funksie wat sal Itereer ten einde die grootste nie-oneindige float waarde vind. Dit kom met 'n konfigureerbare multiplicator en affiene waardes, sodat jy meer CPU om 'n meer akkurate skatting te kry kan deel. Ek havent gesien beter waardes met meer affiene, maar goed, die moontlikheid is hier so as jy regtig iets die moeite werd die SVE-tyd, net probeer om meer affiene. Die beste resultate blyk te wees met mul2 / affine1. Jy kan speel met die waardes en kyk wat jy kry. Die goeie ding is hierdie metode sal werk op enige stelsel. ltphp funksie floatmax (MUL 2. affiene 1) Max 1 omax 0 terwyl ((string) Max INF) vir (i 0 i lt i affiene) pmax 1 Max omax terwyl ((string) Max INF) omax Max Max pmax pmax MUL terugkeer omax GT Wees versigtig wanneer die gebruik van float waardes in stringe wat as kode later gebruik word, byvoorbeeld wanneer genereer JavaScript-kode of SQL-stellings. Die float is eintlik geformateer volgens die blaaier land instelling, wat beteken dat 0,23 tot gevolg sal hê 0,23. Stel jou voor iets soos hierdie: x 0.23 JS var cat doBar (x) te druk JS Dit sal lei tot 'n ander resultaat vir gebruikers met 'n paar locales. Op die meeste stelsels, sal hierdie druk: var cat doBar (0.23), maar wanneer byvoorbeeld 'n gebruiker uit Duitsland kom, sal dit anders wees: var cat doBar (0,23) wat natuurlik 'n ander oproep om die funksie. JavaScript gewoond stel 'n fout, is bykomende argumente weggegooi sonder kennisgewing, maar die funksie doBar (a) sal kry 0 as parameter. Soortgelyke probleme kan nêrens anders ontstaan (SQL, enige tou wat gebruik word as kode elders). Die probleem voortduur, as jy die gebruik. operateur in plaas van die evaluering van die veranderlike in die tou. So as jy regtig nodig het om seker te wees om die string korrek geformateer, gebruik numberformat () om dit te doen Ek is programmering 'n rekeningkundige aansoek MySql wat my nodig is om 'n versameling van dryf som en te verseker dat hulle gelyk nul voor die pleeg van 'n transaksie het, maar soos hierbo 'n bedrag van dryf gesien kan nie altyd vertrou (soos my geval was). Ek het om 'n baie klein restant (soos 1.4512431231e-14). Sedert ek numberformat gebruik het (Num, 2) om die akkuraatheid van die getalle in die databasis opgestel om slegs twee (2) desimale plekke, wanneer die tyd aanbreek om die som ek eenvoudig vermenigvuldig elke getal met tien (10), therby uitskakeling bereken en desimale plekke en laat my met heelgetalle tot my som preform. Dit werk baie goed. ltphp / hex2float (Skakel 8 syfer heksadesimale waarde te dryf (enkel-presisie 32bits) Aanvaar 8 syfer heksadesimale waardes in 'n string gebruik:. hex2float32n (429241f0) gee terug - gt 73,128784179688 / funksie hex2float (aantal) binfinal sprintf (032b hexdec (aantal) ) teken substr (binfinal 0. 1) exp substr (binfinal 1. 8) MANTISSA 1. substr (binfinal 9) MANTISSA strsplit (MANTISSA) exp bindec (exp) -... 127 significand 0 vir (i 0 i LT 24 i ) significand (1 / POW (2. i)) MANTISSA ek terugkeer significand pow (2. exp) (teken - 2 1) GT Die drywende punt presisie boks in die praktyk beteken: Dit eggo (69,1-vloer (69,1)) GT Dink thisll terugkeer 0.1 dit maak nie - dit gee ,099999999999994 dit eggo ronde ((69,1-vloer (69,1))) GT Hierdie opgawes 0.1 en is die tydelike oplossing wat ons gebruik Let daarop dat dit eggo (4.1-vloer (4.1)) GT doen terugkeer 0.1. - so as jy, soos ons, toets dit met 'n lae getalle, jy is nie, net soos ons, verstaan waarom almal van 'n skielike jou script nie meer werk nie, totdat jy 'n baie te spandeer tyd, soos ons, ontfouting dit. So, dis dan al die lieflikheid self. 'N doeltreffende manier om twee reële getalle (insluitend swaai punt nommers) met 'n hoë akkuraatheid te vergelyk en steeds in staat wees om presies te stel met behulp van die BC Math funksie bccomp () Byvoorbeeld: ltphp n 1,23456789 b 1,23456780 presisie 5 As (bccomp (AB presisie) 0) eggo ware // ware GT ltphp n sprintf (.17f. 0.1 0.2) b 0.3 indien (bccomp (AB 17) 0) eggo ONWAAR // ONWAAR GT Skakel 'n blok string in 'n 32-bit IEEE 754 float nommer. Hierdie funksie is 2 keer vinniger as die onderstaande blok te 32bit funksie. Hierdie funksie verander net gegee tik (string na int) keer. Ook hierdie funksie is 'n hawe van die blok te 64bit funksie van onder. ltphp funksie hexTo32Float (strHex) v hexdec (strHex) x (v amp ((1 ltlt 23) - 1)) (1 ltlt 23) (v gtgt 31 1) exp (v gtgt 23 amp 0xFF) - 127 terugkeer x pow ( 2. exp - 23) GT ltphp // voorbeeld eggo hexTo32Float (C4028000) // uitgange: -522 eggo hexTo32Float (457F9000) // uitgange: 4089 ECHO hexTo32Float (2D7F5) // uitgange: 6.00804264307E-39 eggo hexTo32Float (0002D7F5) // uitgange: 6.00804264307E-39 eggo hexTo32Float (47D9F95E) // uitgange: 111.602,734375 GT die funksie gee terug 5 vir 5000, want as daar geen desimale punt, dan is die eerste strpos sal vals is, en valse dit 1 WAAR so die toestand sal steeds waar te wees. Daar moet seker gemaak strpos terug 'n geldige standpunt: ltphp funksie str2num (STR) as (...... Strpos (STR) ONWAAR ampamp strpos (str,) ONWAAR ampamp strpos (STR) Dit strpos (str,)) str strreplace (... str) str strtr (str.,..) anders str strreplace (,.. str) terugkeer (float) str GT PHP skakel van die standaard desimale notasie om eksponensiële notasie vir sekere spesiale dryf. Jy kan 'n gedeeltelike lys van so 'n spesiale waardes met hierdie sien: ltphp vir (TMP 0. i 0 i LT 100 i) tmp 100000 eggo ronde (TMP), N GT Dus, as jy twee dryf voeg, eindig met 'n spesiale waarde , bv Bv NUM.
No comments:
Post a Comment