// inferred from the right hand side of the equals.
bar := 15;
- print("foo is %i\n", foo);
- print("footwo is %i\n", footwo);
- print("bar is %i\n", bar);
+ printf("foo is {}\n", foo);
+ printf("footwo is {}\n", footwo);
+ printf("bar is {}\n", bar);
}
foo := 10;
foo_ptr := ^foo;
- printf("foo is %i\n", foo);
- printf("foo_ptr is %p\n", foo_ptr);
+ printf("foo is {}\n", foo);
+ printf("foo_ptr is {}\n", foo_ptr);
// An important type to know before proceeding is the range type. When designing
// to specify the step in a range literal.
rng := 5 .. 25;
print("rng is ");
- print(rng);
+ println(rng);
// Onyx has 3 different array-like types:
// * Fixed-size arrays, written [N] <type>, where N is a compile time know integer.
for i: 0 .. 10 {
fixed_arr[i] = i * i;
}
- print("fixed_arr[3] is %i\n", fixed_arr[3]);
+ printf("fixed_arr[3] is {}\n", fixed_arr[3]);
// A quick thing to note about fixed size arrays is that they copy their contents
// on assignment. In this example, another_arr declares space on the stack for 10
fixed_arr[3] = 1234;
- printf("another_arr[3] is %i\n", another_arr[3]);
+ printf("another_arr[3] is {}\n", another_arr[3]);
// Slices are a concept not unique to Onyx. They represent a pointer and a count,
// of fixed_arr. It is important to know that this does NOT make a copy of the
// data. It simply points into the same memory as fixed_arr.
slice_arr := fixed_arr[3 .. 9];
- print("slice_arr[3] is %i\n", slice_arr[3]);
+ printf("slice_arr[3] is {}\n", slice_arr[3]);
// Dynamic arrays are the most common arrays used in practice. They represent a
array.push(^dyn_arr, i * i * i);
}
- print("dyn_arr is ");
- print_array(dyn_arr);
+ printf("dyn_arr is {}\n", dyn_arr);
// for i to be 11.
while i := 0; i < 10 {
- printf("%i ", i);
+ printf("{} ", i);
i += 1;
} else {
print("The while loop never ran...");
// break or continue the loop that you want to. Take this example.
while i := 0; i < 10 {
while j := 0; j < 10 {
- printf("%i %j\n", i, j);
+ printf("{} {}\n", i, j);
if i == 1 && j == 2 do break break;
j += 1;
// To access certain elements of the array, simply use the array access operator,
// [...], as so. This sets the fourth element of the array to be 1234.
arr[3] = 1234;
- printf("arr[3] is %i\n", arr[3]);
+ printf("arr[3] is {}\n", arr[3]);
// Fixed-size arrays can be iterated over using a `for` loop as so.
for element: arr {
- printf("%i ", element);
+ printf("{} ", element);
}
- printf("\n");
+ print("\n");
// Fixed-size arrays are passed to procedures by reference. In the following example,
array_proc(arr);
for element: arr {
- printf("%i ", element);
+ printf("{} ", element);
}
// array. Slices and dynamic arrays do not operate this way.
other_arr : [10] i32;
other_arr = arr;
- for other_element: other_arr do printf("%i ", other_element);
- printf("\n");
+ for other_element: other_arr do printf("{} ", other_element);
+ print("\n");
// This does mean that the following pattern of double buffering arrays (which
// is used widely in many C programs), will work in Onyx, but it will be much
// OR
arr_lit := i32.[ 2, 3, 5, 7, 11 ];
- for elem: arr_lit do printf("%i ", elem);
- printf("\n");
+ for elem: arr_lit do printf("{} ", elem);
+ print("\n");
// The type of the elements of the array is given right before the `.`. The
// expression `u32.[ 1, 2, 3, 4, 5 ]` has the type `[5] u32`. The elements
case 5 {
x := math.max(20, 50);
- defer printf("x in case '5' is %i.\n", x);
+ defer printf("x in case '5' is {}.\n", x);
if x >= 40 do fallthrough;
typed_varargs :: (args: ..i32) {
print("Typed variadic arguments: ");
for x: args {
- printf("%i ", x);
+ printf("{} ", x);
}
print("\n");
}
// can be achieved because in Onyx, untyped varargs know how many varargs are passed
// through a runtime count. This means if you call vararg_get more times than there
// are varargs, you will get empty or default results back.
+ //
+ // Most of the time with untyped varargs, you will have some kind of format
+ // specifier to indicate how many and of what type the varargs are. For example
+ // 'printf' used to use this:
+ //
+ // printf :: (format: str, va: ...) -> void
+ // printf("%i %f %l %d", int, float, long, double);
untyped_varargs :: (args: ...) {
print("Untyped variadic arguments: ");
x: i32;
while vararg_get(args, ^x) {
- printf("%p ", x);
+ printf("{} ", cast(rawptr) x);
}
print("\n");
+ // Untyped varargs will remain in the language for now, but a much better approach
+ // has been taken to have mixed type variadic arguments, and it is called 'any'.
+ // This is a procedure that takes a variadic number of 'any's. The powerful fact
+ // about 'any' is that is contains a member called 'type', which can be used to
+ // lookup type information at runtime. 'printf' already uses this for its '{}' format
+ // specifiers, and it knows how to print type names.
+ any_varargs :: (args: ..any) {
+ print("Any variadic arguments: ");
- // Most of the time with untyped varargs, you will have some kind of format
- // specifier to indicate how many and of what type the varargs are. For example
- // 'printf' uses this:
- //
- // printf :: (format: str, va: ...) -> void
- // printf("%i %f %l %d", int, float, long, double);
- //
- // There are plans for the future to have better runtime type information available,
- // which would allow you to introspect the types of each vararg at runtime. This
- // would mean that instead of using '%i' style specifiers in printf, you could use
- // '{}' to indicate the next variadic argument, whose type is automatically determined.
- // If I'm not explaining this very well I apologize and hope that when the feature
- // is implemented, it will make sense why it is a good idea.
+ for arg: args {
+ printf("{}, ", arg.type);
+ }
+
+ print("\n");
+ }
+
+ any_varargs(1, 2.0f, "test", any_varargs);
}
// procedure between two areas of concern.
basically_a_method :: (use dummy: ^Dummy) {
- printf("Dummy with name '%s', and age '%i'.\n", name, age);
+ printf("Dummy with name '{}', and age '{}'.\n", name, age);
}
dummy := Dummy.{ "Phil", 15 };