vaikka ihannetapauksessa MRI ja JRuby käyttäytyisivät 100% samalla tavalla kaikissa tilanteissa, on joitakin pieniä eroja. Jotkut erot johtuvat bugeista, ja niitä ei ole raportoitu täällä. Tämä sivu on eroja, jotka eivät ole vikoja.
Stack Trace Differences
koska JRuby on JVM-pohjainen kieli, saatat nähdä joitakin eroja siinä, miten Ruby stack traces (”backtraces”) on renderoitu. Osittainen luettelo tällaisista tapauksista on alla:
- kohteen rakentamisesta syntyvää” uutta ” kehystä ei välttämättä ole olemassa optimointien vuoksi.
- Java-kielellä toteutetut Ydinluokan menetelmät osoittavat a: n .java-tiedosto ja rivinumero, jossa CRuby vain näytti kutsumuksen .rb-linja kahdesti. Tämän ei pitäisi vaikuttaa
caller
jacaller_locations
tuotokseen. - kehyksiä voi olla enemmän tai vähemmän johtuen siitä, miten rekonstruoimme pinojäljen JVM: n pinosta.
- Pesimälohkot eivät näytä pesinnän tasoa.
- ylätason kehyksissä voi olla eri nimi, jossa CRuby esittää ””.
yleensä koodin ei pitäisi perustua poikkeuksen taustalevyihin, jotka vastaavat täsmälleen Crubya, mutta jos ero on kyseenalainen, avaa bugi. Yritämme löytää Crubyn mahdollisimman läheltä.
Native C Extensions
JRuby ei voi suorittaa native C-laajennuksia. Suositut kirjastot on yleensä siirretty Java-alkuperäisille laajennuksille. Myös nyt, kun FFI on tullut suosittu vaihtoehto Sitominen C kirjastot, käyttämällä sitä poistaa tarpeen kirjoittaa suuri pala natiivi laajennuksia.
Jatkumot ja kuidut
JRuby ei tue jatkumoja(ydin.callcc).
kuidut (eräänlainen rajattu jatke) on tuettu Jrubylla, mutta jokaisen kuidun takana on natiivi säie. Tämä voi johtaa resurssiongelmiin, kun yritetään käyttää enemmän kuituja kuin järjestelmä sallii kierteet tietyssä prosessissa.
vedoten ulkoisiin prosesseihin
Microsoft Windowsissa JRuby on hieman älykkäämpi käynnistäessään ulkoisia prosesseja. Jos suoritustiedosto ei ole binäärinen suoritustiedosto (.exe
), MRI vaatii, että annat myös tiedoston loppuliitteen, mutta JRuby onnistuu ilman sitä.
esimerkiksi sano, että sinulla on tiedosto foo.bat
polullasi ja haluat ajaa sen.
system( 'foo' ) # works on JRuby, fails on MRIsystem( 'foo.bat' ) # works both in JRuby and MRI
haarukkaa ei toteuteta
JRuby ei toteuta fork()
millään alustalla, mukaan lukien sellaiset, joissa fork()
on käytettävissä magneettikuvauksessa. Tämä johtuu siitä, että useimpia JVMs: iä ei voida haaroittaa turvallisesti.
Native Endian on Big Endian
koska JVM esittää jrubylle yhteensopivan suorittimen, jrubyn alkuperäinen endian on Big Endian. Tällä on merkitystä operaatioille, jotka riippuvat tästä käyttäytymisestä, kuten String#unpack
ja Array#pack
formaateille kuten I
, i
, S
, ja s
.
Aikatarkkuus
koska ei ole mahdollista saada usec
tarkkuutta JVM: llä, Time.now.usec
ei voi palauttaa arvoja nanosekunnin tarkkuudella. Näin ei enää ole POSIX-alustan alla (JRuby 9.1: stä lähtien).
irb(main):004:0> Time.now.usec=> 815414
Windowsissa natiivi järjestelmäkutsua ei toteuteta ja näin on JVM: n millisekunnin tarkkuus varasuunnitelma.Pidä tämä mielessä, kun lasket koodisi tarkkuuteen usec
.
> Time.now.usec=> 582000
Säieprioriteetti
HUOM: ainakin jo JRuby 1.7.6: sta lähtien Ruby-säieprioriteetit on yhdistetty Java-säieprioriteettiin, joten tämä osio ei ole tarkka-voit käyttää samaa prioriteettia MRI: ssä ja Jrubyssa.
magneettikuvauksessa Säieprioriteetti voidaan asettaa mihin tahansa arvoon fixnumissa (jos alkuperäiset langat ovat käytössä) tai -3..3 (Jos ei). Oletusarvo on 0.
Jrubyssa kierteet ovat Java-kierteiden tukena, ja prioriteetti vaihtelee 1: stä 10: een, oletusarvo on 5. Jos arvo on tämän alueen ulkopuolella Thread#priority=
, prioriteetiksi asetetaan 1 tai 10.
huomaa: että JVM saattaa jättää prioriteetit huomioimatta, se todella riippuu kohdeos: sta ja (vanhemman) Javan kanssa sinun on läpäistävä ylimääräinen -XX:UseThreadPriorities
, jotta niitä voidaan käyttää.
SystemStackError
JRuby ei pysty pelastamaan SystemStackError
. Jos koodi luottaa tähän, kannattaa mieluummin yrittää saada kiinni Java::JavaLang::StackOverflowError
. Katso lisätietoja tästä Lipusta.
Argumentiton ”proc”
jos annat proc
ilman argumentteja ja menetelmä sattuu läpäistyksi lohkon, Ruby päätyy kaappaamaan läpäistyn lohkon. Jotkut huomaavat tämän ja se johtaa harvinaiseen kuvioon proc.call
. Emme tue tällaista käytöstä. Ongelmana on proc funktiona suhteellisen yleinen, mutta se pakottaa meidät deoptoimaan kaikki proc: n käyttötarkoitukset, kuten proc { #some code }
. Suositeltava työ on ilmoittaa lohko nimenomaisesti käyttäen ampersand def foo(&my_proc)...
. Jos haluat analogisen käyttäytymisen proc, Sallimme myös Proc.new
: n, joka toimii täsmälleen samalla tavalla kuin bare proc-kutsu.