add sources
This commit is contained in:
parent
fcd25eea52
commit
7ce631a648
21 changed files with 548 additions and 2 deletions
|
@ -0,0 +1,33 @@
|
|||
bool find1(int[] haystack, int needle)
|
||||
{
|
||||
foreach (v; haystack)
|
||||
{
|
||||
if (v == needle)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
int[] find2(int[] haystack, int needle)
|
||||
{
|
||||
while (haystack.length > 0 && haystack[0] != needle)
|
||||
{
|
||||
haystack = haystack[1 .. $];
|
||||
}
|
||||
|
||||
return haystack;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int[] a = [];
|
||||
assert(find2(a, 5) == []);
|
||||
a = [ 1, 2, 3 ];
|
||||
assert(find2(a, 0) == []);
|
||||
assert(find2(a, 1).length == 3);
|
||||
assert(find2(a, 2).length == 2);
|
||||
assert(a[0 .. $ - find2(a, 3).length] == [ 1, 2 ]);
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
import std.conv;
|
||||
import std.stdio : stdout;
|
||||
|
||||
void write(T...)(T args)
|
||||
{
|
||||
foreach (arg; args)
|
||||
{
|
||||
stdout.rawWrite(to!string(arg));
|
||||
}
|
||||
}
|
||||
|
||||
void writeln(T...)(T args)
|
||||
{
|
||||
write(args, '\n');
|
||||
stdout.flush();
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
writeln(5, "здравствуй", 4.2);
|
||||
}
|
|
@ -0,0 +1,19 @@
|
|||
import std.stdio, std.typecons;
|
||||
|
||||
void fun(T...)(T args)
|
||||
{
|
||||
// Создать кортеж, чтобы "упаковать" все аргументы в одно значение
|
||||
gun(tuple(args));
|
||||
}
|
||||
|
||||
void gun(T)(T value)
|
||||
{
|
||||
// Расширить кортеж и получить исходное множество параметров
|
||||
writeln(value.expand);
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
fun(1); // Все в порядке
|
||||
fun(1, 2.2); // Все в порядке
|
||||
}
|
|
@ -0,0 +1,16 @@
|
|||
import std.stdio;
|
||||
|
||||
void testing(T...)(T values)
|
||||
{
|
||||
writeln("Переданных аргументов: ", values.length, ".");
|
||||
// Обращение к каждому индексу и каждому значению
|
||||
foreach (i, value; values)
|
||||
{
|
||||
writeln(i, ": ", typeid(T[i]), " ", value);
|
||||
}
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
testing(5, "здравствуй", 4.2);
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
import core.stdc.stdarg, std.conv;
|
||||
|
||||
extern(C) string cToString(string type, ...)
|
||||
{
|
||||
va_list args_list;
|
||||
va_start(args_list, type);
|
||||
scope(exit) va_end(args_list);
|
||||
|
||||
switch (type)
|
||||
{
|
||||
case "int":
|
||||
auto int_val = va_arg!int(args_list);
|
||||
return to!string(int_val);
|
||||
case "double":
|
||||
auto double_val = va_arg!double(args_list);
|
||||
return to!string(double_val);
|
||||
case "complex":
|
||||
auto re_val = va_arg!double(args_list);
|
||||
auto im_val = va_arg!double(args_list);
|
||||
return to!string(re_val) ~ " + " ~ to!string(im_val) ~ "i";
|
||||
case "string":
|
||||
return va_arg!string(args_list);
|
||||
default:
|
||||
assert(0, "Незнакомый тип");
|
||||
}
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
assert(cToString("int", 5) == "5");
|
||||
assert(cToString("double", 2.0) == "2");
|
||||
assert(cToString("string", "Test string") == "Test string");
|
||||
assert(cToString("complex", 3.5, 2.7) == "3.5 + 2.7i");
|
||||
}
|
|
@ -0,0 +1,68 @@
|
|||
import core.stdc.stdarg, std.conv;
|
||||
|
||||
string dToString(string type, ...)
|
||||
{
|
||||
va_list args_list;
|
||||
va_copy(args_list, _argptr);
|
||||
scope(exit) va_end(args_list);
|
||||
|
||||
switch (type) {
|
||||
case "int":
|
||||
assert(_arguments.length == 1 && _arguments[0] is typeid(int), "Аргумент должен иметь тип int.");
|
||||
auto int_val = va_arg!int(args_list);
|
||||
return to!string(int_val);
|
||||
case "double":
|
||||
assert(_arguments.length == 1 && _arguments[0] is typeid(double), "Аргумент должен иметь тип double.");
|
||||
auto double_val = va_arg!double(args_list);
|
||||
return to!string(double_val);
|
||||
case "complex":
|
||||
assert(_arguments.length == 2 && _arguments[0] is typeid(double) && _arguments[1] is typeid(double), "Для типа complex должны быть переданы два аргумента типа double.");
|
||||
auto re_val = va_arg!double(args_list);
|
||||
auto im_val = va_arg!double(args_list);
|
||||
return to!string(re_val) ~ " + " ~ to!string(im_val) ~ "i";
|
||||
case "string":
|
||||
assert(_arguments.length == 1 && _arguments[0] is typeid(string), "Аргумент должен иметь тип string.");
|
||||
return va_arg!string(args_list).idup;
|
||||
default:
|
||||
assert(0);
|
||||
}
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
assert(dToString("int", 5) == "5");
|
||||
assert(dToString("double", 2.0) == "2");
|
||||
assert(dToString("string", "Test string") == "Test string");
|
||||
assert(dToString("complex", 3.5, 2.7) == "3.5 + 2.7i");
|
||||
}
|
||||
|
||||
import std.stdio, std.variant;
|
||||
|
||||
void pseudoVariadic(Variant[] vars)
|
||||
{
|
||||
foreach (var; vars)
|
||||
{
|
||||
if (var.type == typeid(string))
|
||||
{
|
||||
writeln("Строка: ", var.get!string);
|
||||
}
|
||||
else if (var.type == typeid(int))
|
||||
{
|
||||
writeln("Целое число: ", var.get!int);
|
||||
}
|
||||
else
|
||||
{
|
||||
writeln("Незнакомый тип: ", var.type);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void templatedVariadic(T...)(T args)
|
||||
{
|
||||
pseudoVariadic(variantArray(args));
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
templatedVariadic("Здравствуй, мир!", 42);
|
||||
}
|
|
@ -0,0 +1,32 @@
|
|||
import std.stdio;
|
||||
|
||||
ulong fib1(uint n)
|
||||
{
|
||||
return n < 2 ? n : fib1(n - 1) + fib1(n - 2);
|
||||
}
|
||||
|
||||
ulong fib2(uint n)
|
||||
{
|
||||
ulong iter(uint i, ulong fib_1, ulong fib_2)
|
||||
{
|
||||
return i == n ? fib_2 : iter(i + 1, fib_1 + fib_2, fib_1);
|
||||
}
|
||||
return iter(0, 1, 0);
|
||||
}
|
||||
|
||||
pure ulong fib3(uint n)
|
||||
{
|
||||
ulong fib_1 = 1, fib_2 = 0;
|
||||
foreach (i; 0 .. n)
|
||||
{
|
||||
auto t = fib_1;
|
||||
fib_1 += fib_2;
|
||||
fib_2 = t;
|
||||
}
|
||||
return fib_2;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
writeln(fib3(40));
|
||||
}
|
|
@ -0,0 +1,16 @@
|
|||
import std.stdio;
|
||||
|
||||
pure bool leapYear(uint y)
|
||||
{
|
||||
return (y % 4) == 0 && (y % 100 || (y % 400) == 0);
|
||||
}
|
||||
|
||||
pure uint daysInYear(uint y)
|
||||
{
|
||||
return 365 + leapYear(y);
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
writeln(daysInYear(2022));
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
ref int bump(ref int x)
|
||||
{
|
||||
return ++x;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int x = 1;
|
||||
bump(bump(x)); // Два увеличения на 1
|
||||
assert(x == 3);
|
||||
}
|
|
@ -0,0 +1,16 @@
|
|||
// Вычисляет частное и остаток от деления для аргументов a и b.
|
||||
// Возвращает частное по значению, а остаток – в параметре rem.
|
||||
|
||||
int divrem(int a, int b, out int rem)
|
||||
{
|
||||
assert(b != 0);
|
||||
rem = a % b;
|
||||
return a / b;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int r;
|
||||
int d = divrem(5, 2, r);
|
||||
assert(d == 2 && r == 1);
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
void fun(int x)
|
||||
{
|
||||
x += 42;
|
||||
}
|
||||
|
||||
void gun(int[] x)
|
||||
{
|
||||
x = [ 1, 2, 3 ];
|
||||
}
|
||||
|
||||
void hun(int[] x)
|
||||
{
|
||||
x[0] = x[1];
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int x = 10;
|
||||
fun(x);
|
||||
assert(x == 10); // Ничего не изменилось
|
||||
int[] y = [ 10, 20, 30 ];
|
||||
gun(y);
|
||||
assert(y == [ 10, 20, 30 ]); // Ничего не изменилось
|
||||
hun(y);
|
||||
assert(y == [ 20, 20, 30 ]); // Изменилось!
|
||||
}
|
|
@ -0,0 +1,18 @@
|
|||
T[] find(T)(T[] haystack, T needle)
|
||||
{
|
||||
while (haystack.length > 0 && haystack[0] != needle)
|
||||
{
|
||||
haystack = haystack[1 .. $];
|
||||
}
|
||||
return haystack;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
// Проверка способностей к обобщению
|
||||
double[] d = [ 1.5, 2.4 ];
|
||||
assert(find(d, 1.0) == null);
|
||||
assert(find(d, 1.5) == d);
|
||||
string[] s = [ "one", "two" ];
|
||||
assert(find(s, "two") == [ "two" ]);
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
T[] find(T, E)(T[] haystack, E needle)
|
||||
if (is(typeof(haystack[0] != needle) == bool))
|
||||
{
|
||||
while (haystack.length > 0 && haystack[0] != needle)
|
||||
{
|
||||
haystack = haystack[1 .. $];
|
||||
}
|
||||
return haystack;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
// assert(find([1, 2, 3], "Hello"));
|
||||
assert(find([1, 2, 3], 1.0));
|
||||
}
|
|
@ -0,0 +1,27 @@
|
|||
import std.stdio;
|
||||
|
||||
void transmogrify(uint value)
|
||||
{
|
||||
writeln("Вызов функции с uint: ", value);
|
||||
}
|
||||
|
||||
void transmogrify(long value)
|
||||
{
|
||||
writeln("Вызов функции с long: ", value);
|
||||
}
|
||||
|
||||
void transmogrify(T)(T value)
|
||||
{
|
||||
writeln("Вызов функции с T: ", value);
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
transmogrify(42); // Вызывает transmogrify(uint)
|
||||
transmogrify("hello"); // Вызывает transmogrify(T), T=string
|
||||
transmogrify(1.1); // Вызывает transmogrify(T), T=double
|
||||
|
||||
// Вызов функции с uint: 42
|
||||
// Вызов функции с T: hello
|
||||
// Вызов функции с T: 1.1
|
||||
}
|
|
@ -0,0 +1,20 @@
|
|||
T1[] find(T1, T2)(T1[] longer, T2[] shorter)
|
||||
if (is(typeof(longer[0 .. 1] == shorter) : bool))
|
||||
{
|
||||
while (longer.length >= shorter.length)
|
||||
{
|
||||
if (longer[0 .. shorter.length] == shorter)
|
||||
{
|
||||
break;
|
||||
}
|
||||
longer = longer[1 .. $];
|
||||
}
|
||||
return longer;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
double[] d1 = [ 6.0, 1.5, 2.25, 3 ];
|
||||
float[] d2 = [ 1.5, 2.25 ];
|
||||
assert(find(d1, d2) == d1[1 .. $]);
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
import std.stdio;
|
||||
|
||||
T[] find(alias pred, T)(T[] input)
|
||||
if (is(typeof(pred(input[0])) == bool))
|
||||
{
|
||||
for (; input.length > 0; input = input[1 .. $])
|
||||
{
|
||||
if (pred(input[0])) break;
|
||||
}
|
||||
return input;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int[] a = [ 1, 2, 3, 4, -5, 3, -4 ];
|
||||
// Найти первое отрицательное число
|
||||
auto b = find!(function bool(int x) { return x < 0; })(a).dup;
|
||||
writeln(b);
|
||||
auto c = find!((x) { return x > 0; })(b);
|
||||
writeln(c);
|
||||
string[] str = ["one", "two", "ab", "three", "four"];
|
||||
auto d = find!((x) { return x.length == 2; })(str);
|
||||
writeln(d);
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
import std.stdio;
|
||||
|
||||
T[] find(alias pred, T)(T[] input)
|
||||
if (is(typeof(pred(input[0])) == bool))
|
||||
{
|
||||
for (; input.length > 0; input = input[1 .. $])
|
||||
{
|
||||
if (pred(input[0])) break;
|
||||
}
|
||||
return input;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int zero = 0;
|
||||
|
||||
bool isTypeLow(int x)
|
||||
{
|
||||
return x < zero;
|
||||
}
|
||||
|
||||
static bool isTypeBig(int x)
|
||||
{
|
||||
// Из-за static zero не будет видно внутри функции
|
||||
return x > zero;
|
||||
}
|
||||
|
||||
int[] a = [ 1, 2, 3, 4, -5, 3, -4 ];
|
||||
// Найти первое отрицательное число
|
||||
auto b = find!(isTypeLow)(a).dup;
|
||||
writeln(b);
|
||||
auto c = find!(isTypeBig)(b);
|
||||
writeln(c);
|
||||
}
|
|
@ -0,0 +1,15 @@
|
|||
import std.algorithm;
|
||||
|
||||
T[] delegate(T[]) finder(T)(T x)
|
||||
if (is(typeof(x == x) == bool))
|
||||
{
|
||||
return delegate(T[] a) { return find(a, x); };
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
auto d = finder(5);
|
||||
assert(d([1, 3, 5, 7, 9]) == [ 5, 7, 9 ]);
|
||||
d = finder(10);
|
||||
assert(d([1, 3, 5, 7, 9]) == []);
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
import std.stdio;
|
||||
|
||||
@property bool empty(T)(T[] a) { return a.length == 0; }
|
||||
@property ref T front(T)(T[] a) { return a[0]; }
|
||||
void popFront(T)(ref T[] a) { a = a[1 .. $]; }
|
||||
|
||||
R find(R, T)(R haystack, T needle)
|
||||
if (is(typeof(haystack.front != needle) == bool))
|
||||
{
|
||||
while (!haystack.empty && haystack.front != needle)
|
||||
{
|
||||
haystack.popFront();
|
||||
}
|
||||
return haystack;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
writeln(find([1, 2, 3], 2.0));
|
||||
assert(find([1, 2, 3], 1.0));
|
||||
}
|
|
@ -0,0 +1,40 @@
|
|||
// import std.range;
|
||||
|
||||
// V reduce(alias fun, V, R)(V x, R range)
|
||||
// if (isInputRange!R && is(typeof(x = fun(x, range.front))))
|
||||
// {
|
||||
// for (; !range.empty; range.popFront())
|
||||
// {
|
||||
// x = fun(x, range.front);
|
||||
// }
|
||||
|
||||
// return x;
|
||||
// }
|
||||
|
||||
@property bool empty(T)(T[] a) { return a.length == 0; }
|
||||
@property ref T front(T)(T[] a) { return a[0]; }
|
||||
void popFront(T)(ref T[] a) { a = a[1 .. $]; }
|
||||
|
||||
V reduce(alias fun, V, R)(V x, R range)
|
||||
if (is(typeof(x = fun(x, range.front)))
|
||||
&& is(typeof(range.empty) == bool)
|
||||
&& is(typeof(range.popFront())))
|
||||
{
|
||||
for (; !range.empty; range.popFront())
|
||||
{
|
||||
x = fun(x, range.front);
|
||||
}
|
||||
|
||||
return x;
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
int[] r = [ 10, 14, 3, 5, 23 ];
|
||||
// Вычислить сумму всех элементов
|
||||
int sum = reduce!((a, b) { return a + b; })(0, r);
|
||||
assert(sum == 55);
|
||||
// Вычислить минимум
|
||||
int min = reduce!((a, b) { return a < b ? a : b; })(r[0], r);
|
||||
assert(min == 3);
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue