% \iffalse meta-comment % (The MIT License) % % Copyright (c) 2021-2022 Yegor Bugayenko % % Permission is hereby granted, free of charge, to any person obtaining a copy % of this software and associated documentation files (the 'Software'), to deal % in the Software without restriction, including without limitation the rights % to use, copy, modify, merge, publish, distribute, sublicense, and/or sell % copies of the Software, and to permit persons to whom the Software is % furnished to do so, subject to the following conditions: % % The above copyright notice and this permission notice shall be included in all % copies or substantial portions of the Software. % % THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR % IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, % FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE % AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER % LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, % OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE % SOFTWARE. % \fi % \CheckSum{0} % % \CharacterTable % {Upper-case \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z % Lower-case \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z % Digits \0\1\2\3\4\5\6\7\8\9 % Exclamation \! Double quote \" Hash (number) \# % Dollar \$ Percent \% Ampersand \& % Acute accent \' Left paren \( Right paren \) % Asterisk \* Plus \+ Comma \, % Minus \- Point \. Solidus \/ % Colon \: Semicolon \; Less than \< % Equals \= Greater than \> Question mark \? % Commercial at \@ Left bracket \[ Backslash \\ % Right bracket \] Circumflex \^ Underscore \_ % Grave accent \` Left brace \{ Vertical bar \| % Right brace \} Tilde \~} % \GetFileInfo{eolang.dtx} % \DoNotIndex{\endgroup,\begingroup,\let,\else,\s,\n,\r,\\,\1,\fi} % \iffalse %<*driver> \ProvidesFile{eolang.dtx} % %\NeedsTeXFormat{LaTeX2e} %\ProvidesPackage{eolang} %<*package> [2022-10-25 0.0.2 Formulas and Graphs for EO Programming Language] % %<*driver> \documentclass{ltxdoc} \usepackage[maxnames=1,minnames=1,maxbibnames=1,natbib=true,citestyle=authoryear,bibstyle=authoryear,doi=false,url=false,isbn=false,isbn=false]{biblatex} \addbibresource{main.bib} \usepackage[tt=false, type1=true]{libertine} \usepackage{microtype} \usepackage{graphicx} \usepackage[runs=1,dtx]{docshots} \usepackage{eolang} \usepackage{href-ul} \PageIndex \EnableCrossrefs \CodelineIndex \RecordChanges \begin{document} \DocInput{eolang.dtx} \PrintChanges \PrintIndex \end{document} % % \fi % \title{\includegraphics[height=1in]{cactus.pdf} \\ |eolang|: \LaTeX{} Package \\ for Formulas and Graphs \\ of EO Programming Language \\ and $\varphi$-calculus\thanks{The sources are in GitHub at \href{https://github.com/objectionary/eolang.sty}{objectionary/eolang.sty}}} % \author{Yegor Bugayenko \\ \texttt{yegor256@gmail.com}} % \date{\filedate, \fileversion} % % \maketitle % % \textbf{NB!} % You must run \TeX{} processor with |--shell-escape| option % and you must have \href{https://www.perl.org}{Perl} installed. % \section{Introduction} % % This package helps you print formulas of $\varphi$-calculus, % which is a formal foundation of \href{https://www.eolang.org}{EO} % programming language. The calculus was introduced by \citet{bugayenko2021eolang} % and later formalized by \citet{kudasov2021}. Here is how you render % a simple expression: % \begin{docshot} % \documentclass{article} % \pagestyle{empty} % \usepackage{eolang} % \begin{document} % \begin{phiquation*} % a -> [[ % ^ !-> $.b, % b -> [[ c -> |fn|(56), % @ -> |hello|($), % \Delta ~> |01-FE-C3| ]]]], % x -> [[ \alpha_0 -> ? ]] % \end{phiquation*} % \end{document} % \end{docshot} % \DescribeEnv{phiquation} % The environment |phiquation| lets you write a $\varphi$-calculus expressions % using simple plain-text notation, where: % \begin{itemize}\setlength\itemsep{0em} % \item ``|@|'' maps to ``$\varphi$'' % (|\varphi|), % \item ``|^|'' maps to ``$\rho$'' % (|\rho|), % \item ``|$|'' maps to ``$\xi$'' % (|\xi|), % \item ``|&|'' maps to ``$\sigma$'' % (|\sigma|), % \item ``|?|'' maps to ``$\varnothing$'' % (|\varnothing|), % \item ``|->|'' maps to ``$\mapsto$'' % (|\mapsto|), % \item ``|!->|'' maps to ``$\mapstochar\relbar\mathrel{\mkern-12mu}\mapsto$'' % (|\mapstochar\relbar\mathrel{\mkern-12mu}\mapsto|), % \item ``|~>|'' maps to ``$\mapstochar\dashrightarrow$'' % (|\mapstochar\dashrightarrow|), % \item ``|[[|'' maps to ``$\llbracket$'' % (|\llbracket|), % \item ``|]]|'' maps to ``$\rrbracket$'' % (|\rrbracket|), % \item ``$\vert$|abc|$\vert$'' maps to ``\texttt{abc}'' % (|\texttt{abc}|). % \end{itemize} % Also, a few symbols are supported for $\varphi$PU architecture: % \begin{itemize}\setlength\itemsep{0em} % \item ``|-abc>|'' maps to ``$\xrightarrow{\text{\sffamily\scshape abc}}$'' % (|\xrightarrow{\text{\sffamily\scshape abc}}|), % \item ``|:=|'' maps to ``$\vDash$'' % (|\vDash|). % \end{itemize} % \DescribeMacro{\phiq} % The command |\phiq| lets you inline a $\varphi$-calculus expressions % using the same simple plain-text notation: % \begin{docshot} % \documentclass{article} % \usepackage[paperwidth=2in]{geometry} % \pagestyle{empty} % \usepackage{eolang} % \begin{document} % A simple object % \phiq{x -> [[@ -> y]]} % is a decorator of % the data object % \phiq{y -> [[\Delta ~> 42]]}. % \end{document} % \end{docshot} % \DescribeEnv{sodg} % The environment |sodg| allows you to draw a \href{https://github.com/objectionary/sodg}{SODG} graph: % \begin{docshot} % \documentclass{article} % \pagestyle{empty} % \usepackage{eolang} % \begin{document} % \begin{sodg} % v0 % v1 xy:v0,-2,+1 data:|42| % v0->v1 a:$x$ rho % v2 xy:v0,+1,+1 atom:$\xi.x+1$ % v1->v2 a:|hi| bend:-15 % v2->v0 pi bend:10 % \end{sodg} % \end{document} % \end{docshot} % The content of the environment is parsed line by line. Markers in each line are % separated by a single space. The first marker is either a unique name of a % vertex, like |v1| in the example above, or an edge, like |v0->v1|. All other markers are either % unary like |rho| or binary like |atom:$\xi.x+1$|. Binary markers have two % parts, separated by colon. The following markers are supported for a vertex: % \begin{itemize}\setlength\itemsep{0em} % \item ``|data:[]|'' makes it a data vertex with an optional attached ||, % \item ``|atom:[]|'' makes it an atom with an optional attached ||, % \item ``|box:|'' attaches a || to it, % \item ``|xy:,,|'' places this vertex in a position relative to the vertex ||, % shifting it right by || % and down by || centimetres. % \end{itemize} % The following markers are supported for an edge: % \begin{itemize}\setlength\itemsep{0em} % \item ``|rho|'' places a backward snake arrow to the edge, % \item ``|rrho|'' places a reverse |rho|, % \item ``|bend:|'' bend it right by the amount of ||, % \item ``|a:|'' attaches label || to it, % \item ``|pi|'' makes it dotted, with $\pi$ label. % \end{itemize} % \StopEventually{} % \section{Implementation} % First, we include a few packages: % \begin{macrocode} \RequirePackage{stmaryrd} \RequirePackage{amsmath} \RequirePackage{amssymb} \RequirePackage{amsfonts} \RequirePackage{iexec} \RequirePackage{fancyvrb} % \end{macrocode} % \begin{macro}{\eolang@env} % \changes{0.0.2}{2022/10/21}{The symbols ``['' and ``]'' replaced with ``[['' and ``]]'' for abstract object brackets, because they conflicted with normal square brackets} % \changes{0.0.2}{2022/10/21}{New symbol added for basket slots} % \changes{0.0.2}{2022/10/21}{Parsing of symbols ``@,'' ``\^{},'' and ``\&'' enabled (varphi, rho, and sigma)} % Then, we define |\eolang@env| supplementary command. % It is implemented with the help of |\iexec| from % \href{https://github.com/yegor256/iexec}{iexec} package: % \begin{macrocode} \makeatletter\newcommand\eolang@env[2]{ \iexec[trace]{ /bin/echo -n '\\begin{#1}\\begin{split} &' && /bin/echo -n '\detokenize{#2}' | perl -pe 's/^\\r\\+//g' | perl -pe 's/\\r\\+$//g' | perl -pe 's/\\?/\\\\varnothing/g' | perl -pe 's/@/\\\\varphi/g' | perl -pe 's/&/\\\\sigma/g' | perl -pe 's/\\^/\\\\rho/g' | perl -pe 's/\\$/\\\\xi/g' | perl -pe 's/-([a-z]+)>/\\\\xrightarrow{\\\\text{\\\\sffamily\\\\scshape \\1}}/g' | perl -pe 's/!->/\\\\mapstochar\\\\relbar\\\\mathrel{\\\\mkern-12mu}\\\\mapsto/g' | perl -pe 's/->/\\\\mapsto/g' | perl -pe 's/:=/\\\\vDash/g' | perl -pe 's/\unexpanded{~}>/\\\\mapstochar\\\\dashrightarrow/g' | perl -pe 's/\\|([^\\|]+)\\|/\\\\texttt{\\1}/g' | perl -pe 's/\\[\\[/\\\\llbracket/g' | perl -pe 's/\\]\\]/\\\\rrbracket/g' | perl -pe 's/\\r\\r/\\\\\\\\ \&/g' | perl -pe 's/\\r/\\\\\\\\[-4pt] \&/g' | perl -pe 's/([^& ]) {2}([^ ])/\\1 \\2/g' | perl -pe 's/ {2}/\\\\quad{}/g' && /bin/echo -n '\\end{split}\\end{#1}\\endinput' }% }\makeatother % \end{macrocode} % \end{macro} % \begin{macro}{phiquation} % Then, we define |phiquation| and |phiquation*| environments: % \begin{macrocode} \makeatletter \NewDocumentEnvironment{phiquation*}{b}{% \eolang@env{equation*}{#1} }{} \NewDocumentEnvironment{phiquation}{b}{% \eolang@env{equation}{#1} }{} \makeatother \AddToHook{env/phiquation*/begin}{\obeylines\obeyspaces} \AddToHook{env/phiquation/begin}{\obeylines\obeyspaces} % \end{macrocode} % \end{macro} % \begin{macro}{\phiq} % \changes{0.0.2}{2022/10/21}{Parsing of additional symbols enabled} % Then, we define |\phiq| command: % \begin{macrocode} \newcommand\phiq[1]{ \iexec[trace]{ /bin/echo -n '$' && /bin/echo -n '\detokenize{#1}' | perl -pe 's/\\^/\\\\rho/g' | perl -pe 's/\\$/\\\\xi/g' | perl -pe 's/&/\\\\sigma/g' | perl -pe 's/\\?/\\\\varnothing/g' | perl -pe 's/@/\\\\varphi/g' | perl -pe 's/!->/\\\\mapstochar\\\\relbar\\\\mathrel{\\\\mkern-12mu}\\\\mapsto/g' | perl -pe 's/->/\\\\mapsto/g' | perl -pe 's/-([a-z]+)>/\\\\xrightarrow{\\\\text{\\\\sffamily\\\\scshape \\1}}/g' | perl -pe 's/\unexpanded{~}>/\\\\mapstochar\\\\dashrightarrow/g' | perl -pe 's/:=/\\\\vDash/g' | perl -pe 's/\\[\\[/\\\\llbracket/g' | perl -pe 's/\\]\\]/\\\\rrbracket/g' && /bin/echo -n '$\\endinput' }% } % \end{macrocode} % \end{macro} % \begin{macro}{Perl} % \changes{0.0.2}{2022/10/24}{The Perl file now has a fixed name, which doesn't depend on the name of the TeX job. This file may be shared among jobs, no need to make it uniquely named.} % Then, create a Perl script: % \begin{macrocode} \begin{VerbatimOut}{eolang.pl} $tex = $ARGV[0]; $tex =~ s/^\s+|\s+$//g; $tex =~ s/(\\[a-zA-Z]+)\s+/\1/g; $tex =~ s/\r\s+/\r/g; $tex =~ s/\|([^\|]+)\|/\\texttt{\1}/g; my @cmds = split (/\r/g, $tex); print '\begin{phig}', "\n"; foreach my $c (@cmds) { my ($head, $tail) = split (/ /, $c, 2); my %opts = {}; foreach my $p (split (/ /, $tail)) { my ($q, $t) = split (/:/, $p); $opts{$q} = $t; } if (index($head, '->') == -1) { print '\node['; if (exists $opts{'xy'}) { my ($v, $right, $down) = split(/,/, $opts{'xy'}); print ',below right='; print $down; print 'cm and '; print $right; print 'cm of '; print $v; } if (exists $opts{'data'}) { print ',phi-data'; if (not $opts{'data'} eq '') { $opts{'box'} = $opts{'data'}; } } elsif (exists $opts{'atom'}) { print ',phi-atom'; if (not $opts{'atom'} eq '') { $opts{'box'} = $opts{'atom'}; } } else { print ',phi-object'; } print ']'; print ' (', $head, ')'; print ' {$'; if ($head eq 'v0') { print '\Phi'; } else { print 'v_', substr($head, 1); } print '$}'; if (exists $opts{'box'}) { print ' node[phi-box] at ('; print $head, '.south east) {'; print $opts{'box'}, '}'; } } else { print '\draw['; if (exists $opts{'pi'}) { print ',phi-pi'; if (not exists $opts{'a'}) { $opts{'a'} = '$\pi$'; } } print ']'; my ($from, $to) = split (/->/, $head); print ' (', $from, ') '; if (exists $opts{'bend'}) { print 'edge [bend right=', $opts{'bend'}, ']'; } else { print '--'; } if (exists $opts{'rho'} or exists $opts{'rrho'}) { print ' pic[sloped,phi-rho]{parallel arrow={'; print '-' if not exists $opts{'rrho'}; print '0.3,-0.15}}'; } if (exists $opts{'a'}) { print ' node [phi-attr] {', $opts{'a'}, '}'; } print ' (', $to, ')'; } print ";\n"; } print '\end{phig}', "\n", '\endinput'; \end{VerbatimOut} \message{^^Jeolang: File with Perl script (eolang.pl) saved^^J}% \iexec[trace,null]{perl -pi -e 's/(\\\\[a-zA-Z])\\s+/\\1/g' eolang.pl} % \end{macrocode} % \end{macro} % \begin{macro}{tikz} % Then, we include |tikz| package and its libraries: % \begin{macrocode} \RequirePackage{tikz} \usetikzlibrary{arrows} \usetikzlibrary{shapes} \usetikzlibrary{decorations} \usetikzlibrary{decorations.pathmorphing} \usetikzlibrary{intersections} \usetikzlibrary{positioning} \usetikzlibrary{calc} \usetikzlibrary{shapes.arrows} % \end{macrocode} % \end{macro} % \begin{macro}{phig} % Then, we define internal environment |phig|: % \begin{macrocode} \newenvironment{phig}% {\noindent\begin{tikzpicture}[ ->,>=stealth',node distance=0,thick, pics/parallel arrow/.style={ code={\draw[-latex,phi-rho] (##1) -- (-##1);}}]}% {\end{tikzpicture}} \tikzstyle{transforms} = [fill=white!80!black, single arrow, minimum height=0.5cm, minimum width=0.5cm, single arrow head extend=2mm] \tikzstyle{phi-thing} = [thick,inner sep=0pt,minimum height=2.4em, draw,font={\small}] \tikzstyle{phi-object} = [phi-thing,circle] \tikzstyle{phi-data} = [phi-thing,regular polygon, regular polygon sides=8] \tikzstyle{phi-empty} = [phi-object] \tikzstyle{phi-rho} = [draw,decorate,decoration={ snake,amplitude=.4mm,segment length=2mm,post length=1mm}] \tikzstyle{phi-pi} = [draw,dotted] \tikzstyle{phi-atom} = [phi-object,double] \tikzstyle{phi-box} = [xshift=-5pt,yshift=3pt,draw,fill=white, rectangle,thin,minimum width=1.2em,anchor=north west, font={\scriptsize}] \tikzstyle{phi-attr} = [midway,sloped,inner sep=0pt, above=2pt,sloped/.append style={transform shape}, font={\scriptsize},color=black] % \end{macrocode} % \end{macro} % \begin{macro}{sodg} % \changes{0.0.2}{2022/10/20}{The environment ``phigure'' renamed to ``sodg'' for the sake of better semantic. The graph in the picture is solely a SODG graph, that's why the name ``sodg'' is better.} % Then, create a new environment |sodg|, as suggested % \href{https://tex.stackexchange.com/questions/661056}{here}: % \begin{macrocode} \NewDocumentEnvironment{sodg}{b}{% \catcode`\ =10 % \catcode`\^^M=5 % \iexec[trace,stdout=\jobname.tex.eolang]{ perl eolang.pl '\detokenize{#1}'}% }{} \AddToHook{env/sodg/before}{\bgroup\obeylines\obeyspaces} \AddToHook{env/sodg/after}{\egroup} % \end{macrocode} % \end{macro} % \Finale % \clearpage % \printbibliography % \clearpage % \PrintChanges % \clearpage % \PrintIndex