( uid_21365 | 2020. 12. 31., cs – 00:35 )

Na itt máris kiviláglik a Peri egyik roppant előnye: a felvetett probléma egyszerűen nem fordulhat elő, tekintettel arra a roppant jóságra, hogy a Periben a ciklusoknak saját külön automatikusan generált ciklusváltozójuk van, ami egyszerűen el se érhető a cikluson kívülről, semmiféle módon se! (Még csak nem is olvasható). Azaz, íme a te programod Peri megfelelője, megcsináltam a tisztletedre:

###sysinclude standard.uh
###sysinclude math.uh
#d
sbr §mypi
@mypi printnl
end
mypi:
zero#d mypi
one#d ss
1000 {{
@ss 2. {{}} #g !(#d) * 1. + / sum mypi
-3. inv prd ss
}}
12. sqr prd mypi
rts
{ „mypi” }
{ „ss” }

A fenti Peri kódban a ciklusváltozó értékét a {{}} szimbólummal kérdezzük le, azaz ez felel meg a te kódod "i" ciklusváltozójának, de ez csak és kizárólag a cikluson belül valid, ha e szimbólumot cikluson kívül alkalmazzuk, a kódunk le se fordul, hanem hibajelzést kapunk... Eképp elő se fordulhat hogy a ciklusváltozó miatt bajba kerülnénk a szubrutinban. A főprogram nyugodtan hívogathatja ha akarja a szubrutinunkat akár ciklusból is, ahol ő is használja a {{}} szimbólumot, semmi baj, mert olyankor e szimbólum a főprogram ciklusváltozójának értékét jelenti majd a főprogram számára...

Ez olyan, mintha a ciklusoknak a Peri nyelvben saját névterük lenne, ami azonban egyetlen változót tartalma, a ciklusváltozót. Pontosabban, mintha a ciklusokon belül az épp aktuális névtér mindig kibővülne az épp futó ciklus ciklusváltozójával. Természetesen ez a {{}} readonly a cikluson belül.

Minthogy a ciklusváltozó amikor lekérdezzük, mindig egy unsigned long long értéket ad vissza, ezt double értékké kell konvertálni, ezt végzi el az utánna álló #g !(#d) utasítássorozat. A #g azt mondja hogy a stack tetején álló érték most épp unsigned long long típusú, a (#d) azt hogy double-vá kell konvertálni, a felkiáltójel meg a zárójel előtt azért kell mert az azt mondja hogy a castolás után maradjon az interpreter ebben a „double” üzemmódban, azaz amíg mást nem mondunk neki minden műveletet double-ként hajtson végre.

Note: A math.uh fájl behúzása elhagyható lenne, ha a 12. lebegőpontos szám négyzetgyökét nem runtime számolnánk ki a

12. sqr

utasítással, hanem konstansként írnánk bele a kódba.

És nézd csak meg a Peri másik előnyét: amit te ilyen bonyolultan írtál:

70 let s = -s/3.0

Az a Periben ennyi:

-3. inv prd ss

Note2: Ettől még értem a problémádat. Ilyen komplexitású feladatot azért már én is inkább függvénybe szerveznék ki, nem szubrutinba, szóval béke van remélem! :)

Jellemzően én akkor használok szubrutinokat, ha azoknak nincs is semmi belső változóigényük, vagy maximum (mint ebben az esetben bemutattam) ciklusváltozóra van igényük, ez ugyanis mint látod a Peri sajátosságai miatt teljesen biztonságos mert úgyis minden ciklusnak külön ciklusváltozója van, fizikailag teljesen elszeparálva minden mástól. És el se érhetőek a cikluson kívülről, de még cikluson belül is csak olvashatóak.