Nytril: A programming language and a markup language in one
Posted by Impressive-Gear-4334@reddit | programming | View on Reddit | 4 comments
Nytril has a unique syntax that makes it easy to create complex documents from the results of your code. There are no "Write" or "Print" statements. The results of each expression simply become a part of the document.
Here are some of the standout features and new concepts:
global functions and namespaces
Nytril allows global functions that do not belong to a class and have no 'this' pointer. They can also be defined inside of a namespace.
F1(x) = x + 1; // F1 defined globally
N1.F2(x) = x + 2; // F2 defined inside the namespace N1
namespace N2 {
F3(x) = x + 3; // F3 defined inside the namespace N2
}
namespace N2 { // N2 can be repeated
F4(x) = x + 4; // F3 and F4 are now a part of N2
}
readonly global functions
If a global function is marked as readonly
, then the function is run the first time it is called anywhere in the program, and the return value is cached. If the function is called again anywhere, the cached value from the first run is returned immediately. This is useful when loading large constant values such as images or the results of database queries or REST calls, where the intention is usually to retrieve information once and then use the same copy for many calculations.
readonly Data = ComplexSlowQuery; // Run only once
readonly Cost = Data.Quantity * Data.Price; // Use like a variable
Affinity operator
To create complex formatted text in an easy way, Nytril introduced the affinity operator. In most programming languages, two operands must be separated by a binary operator (e.g. x * y) or else there is a syntax error. In Nytril, if the compiler encounters two operands without a binary operator between them, it inserts an invisible binary 'affinity' operator and continues without error. At runtime, the type of the two operands is assessed and if an affinity exists between the two types, the operation is executed. If there is no affinity between the types, there is a runtime error.
"123" "abc"
⇒ "123" + "abc"
3 meters
⇒ 3 * meters
Nytril allows the programmer to add left and right affinity between objects of different types, which can create a complex sub-grammar in the language which can increase clarity.
The 'each' Operator
The each
operator is used to call a function with a parameter once for every item in an array. The resulting expression is an array of function return values.
Square(x) = x * x;
Square(each [1, 2, 3, 4]);
⇒ [1, 4, 9, 16]
If a function has more than 1 parameter, the each operator can be used on more than 1 argument. This raises the dimension of the output array.
Power(x, power) = x ^ power;
Power(each [1, 2, 3], each [1, 2, 3]);
⇒ [[1, 4, 9], [1, 4, 9], [1, 8, 27]];
Most unary and binary operators can also be used in conjunction with the each operator to provide a very compact expression.
(each [1, 2, 3]) ^ (each [1, 2, 3])
⇒ [[1, 2, 3], [1, 4, 9], [1, 8, 27]];
Revisions
A revision is a collection of properties and elements inside curly braces {}
that are separated by semi-colons (;}. A property is a "name: value" pair such as TextHeight: 12 pts
. An element is any other expression, including variables and values returned from function calls. The properties and elements of a revision are computed at runtime, so a revision "executes" just like a scope in a function.
A revision adds elements to, and modifies the properties of, format objects in a document. A revision acts on the format object to its left, without modifying it. The combination of the left-hand operand and the right-hand revision is a new revised object that has the properties and elements of the left-hand format/revision plus any additional elements of the right-hand revision, and the added (or overridden) properties of the right-hand revision. By stacking and combining revisions, hierarchical style dictionaries can be created easily in a manner that is similar to Cascading Style Sheets or to the way word processors allow styles to inherit from each other and override properties.
The following code creates a empty Paragraph
and revises it with content and properties. The placement of properties has no effect, but the placement of elements is always in order.
Paragraph {1; 2; 3; "abc"; TextColor: Colors.Blue};
⇒ 123abc
The following code creates a paragraph 'style' called Heading1 by revising the Paragraph
format with several properties. It then uses the Heading1 style by revising it with a string element.
Heading1 = Paragraph {TextColor: Colors.Green; TextWeight: Bold};
Heading1 {"Chapter 1"};
⇒ Chapter 1
Revisions + arrays
Special treatment is given to elements in a revision that are arrays. In this case, all of the elements of the array become elements of the revision, without changing the array. Combining this mechanism with the each
operator, described above, allows for the succinct inclusion of iterated content.
Paragraph {
Square(each [1, 2, 3, 4, 5]);
Separator: ", ";
};
⇒ 1, 4, 9, 16, 25
Revisions with if/else
If statements can be used in a revision to programmatically include or exclude properties and elements from a revision based on a condition.
ShowCount(count) = Paragraph {
"The count is "; count;
if (count > 10)
" and it's too big.";
else
TextColor: Colors.Green;
};
ShowCount(5);
ShowCount(20);
⇒ The count is 5
The count is 20 and it's too big.
Revisions with loops
for
, foreach
, do
and while
loop statements can be used in a revision to iteratively add elements.
ShowNumbers(int count) = Paragraph {
Separator: ", ";
for (int i = 0; i < count; ++i)
for (int j = 0; j < count; ++j)
i * j; // This value gets added for each pass of the inner loop
};
ShowNumbers(4);
⇒ 0, 0, 0, 0, 0, 1, 2, 3, 0, 2, 4, 6, 0, 3, 6, 9
edover@reddit
At first, I wasn't sure why anyone would post a video instead of linking to a website, repository, documentation, or literally anything else. Then I found the website and my god, it's awful.
It feels like it's pre-set to a zoom of like 300%. Until you click on literally anything and discover it's meant to be viewed in two panes. On top of that, it has the most pointless menu-interface/UX I've ever experienced, and the documentation is basically a slide show.
Hard Pass.
Impressive-Gear-4334@reddit (OP)
It seems that you may have missed the main event. Nytril is a desktop application, not a web app. The website has a prominent link to install the desktop software. Did you install the desktop software?
If you had, you would have seen that there is a hundred-page tutorial on the language and dozens of examples. Please give it another go.
iris700@reddit
Name sounds like a drug
Impressive-Gear-4334@reddit (OP)
It's a pun: Replacement for LaTeX.