"Mixin is not defined" error when trying to use template mixins
There's a template mixin in my dimage project's new version in base.d, and when I try to access it from another file I get two errors: undefined identifier `ChunkyAccess4bit`, did you mean template `ChunkyAccess4Bit()`? and mixin `dimage.tga.TGA.ChunkyAccess4bit!()` is not defined Should I put the template into the base class of TGA (Image) instead of keeping it outside of that?
Re: Using a char value >= 128
On Sunday, October 27, 2019 6:44:05 AM MDT Per Nordlöw via Digitalmars-d- learn wrote: > In which circumstances can a `char` be initialized a non-7-bit > value (>= 128)? Is it possible only in non-@safe code? > > And, if so, what will be the result of casting such a value to > `dchar`? Will that result in an exception or will it interpret > the `char` using a 8-bit character encoding? > > I'm asking because I'm pondering about how to specialize the > non-7-bit `needle`-case of the following array-overload of > `startsWith` when `T` is `char`: > > bool startsWith(T)(scope const(T)[] haystack, > scope const T needle) > { > static if (is(T : char)) { assert(needle < 128); } // TODO > convert needle to `char[]` and call itself > if (haystack.length >= 1) > { > return haystack[0] == needle; > } > return false; > } char is a value above 127 all the time, because specific values above 127 are used as the first byte in a multibyte code point in UTF-8. Also, as Adam points out, the default value for char is 255 (in order to specifically give it an invalid value). That being said, it doesn't make sense to use startsWith with a single char which isn't ASCII, because no such char would be valid UTF-8 on its own. - Jonathan M Davis
Re: The compiler can't "see" an inner class
On Sunday, 27 October 2019 at 19:54:06 UTC, Simen Kjærås wrote: It's a bug: interface A { interface B : A { class C : B { } } // Fails: no property 'C' for type 'foo.A.B' void inside(A.B.C c) { } } // Works void outside(A.B.C c) { } https://issues.dlang.org/show_bug.cgi?id=20329 -- Simen Yikes! Thanks for submitting the issue to bugzilla :)
Re: The compiler can't "see" an inner class
On Sunday, 27 October 2019 at 17:52:51 UTC, Emmanuelle wrote: Hello! See snippet: --- interface AST { static interface Expr : AST { final static class Name : Expr { override void accept(AST.Visitor v) { v.visitName(this); } } } final static class Visitor { void visitName(AST.Expr.Name name); } void accept(AST.Visitor v); } --- If you try to compile that, dmd v2.088.0 complains: --- Error: no property Name for type onlineapp.AST.Expr --- How come? It's defined right there. I would really like some pointers on this, thanks! It's a bug: interface A { interface B : A { class C : B { } } // Fails: no property 'C' for type 'foo.A.B' void inside(A.B.C c) { } } // Works void outside(A.B.C c) { } https://issues.dlang.org/show_bug.cgi?id=20329 -- Simen
The compiler can't "see" an inner class
Hello! See snippet: --- interface AST { static interface Expr : AST { final static class Name : Expr { override void accept(AST.Visitor v) { v.visitName(this); } } } final static class Visitor { void visitName(AST.Expr.Name name); } void accept(AST.Visitor v); } --- If you try to compile that, dmd v2.088.0 complains: --- Error: no property Name for type onlineapp.AST.Expr --- How come? It's defined right there. I would really like some pointers on this, thanks!
Re: Supporting inout haystack in array-overload of findSplitBefore without template-bloat
On Sunday, 27 October 2019 at 14:57:29 UTC, Per Nordlöw wrote: @safe pure nothrow @nogc unittest { auto r = "a*b".findSplitAfter_inout('*'); static assert(is(typeof(r.pre()) == string)); assert(r); assert(r.pre == "a*"); assert(r.post == "b"); } Made it work! :) /** Array-overload for `findSplitAfter` with default predicate. * * See_Also: https://forum.dlang.org/post/dhxwgtaubzbmjaqjm...@forum.dlang.org */ auto findSplitAfter(T)(scope inout(T)[] haystack, // TODO support inout? See_Also: https://forum.dlang.org/post/jtpchtddgenhjuwhq...@forum.dlang.org scope const T needle) @trusted { static struct Result { private T[] _haystack; private size_t _offset; pragma(inline, true): inout(T)[] pre() @trusted inout { if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[0 .. _offset + 1]; } inout(T)[] post() @trusted inout { if (_isMiss) { return _haystack[0 .. $]; } return _haystack.ptr[_offset + 1 .. _haystack.length]; } bool opCast(T : bool)() const { return !_isMiss; } private bool _isMiss() const { return _haystack.length == _offset; } } foreach (const offset, const ref e; haystack) { if (e == needle) { return inout(Result)(haystack, offset); } } return inout(Result)(haystack, haystack.length); } /// @safe pure nothrow @nogc unittest { char[] haystack; auto r = haystack.findSplitAfter('*'); static assert(is(typeof(r.pre()) == char[])); static assert(is(typeof(r.post()) == char[])); } /// @safe pure nothrow @nogc unittest { const(char)[] haystack; auto r = haystack.findSplitAfter('*'); static assert(is(typeof(r.pre()) == const(char)[])); static assert(is(typeof(r.post()) == const(char)[])); } /// @safe pure nothrow @nogc unittest { auto r = "a*b".findSplitAfter('*'); static assert(is(typeof(r.pre()) == string)); static assert(is(typeof(r.post()) == string)); assert(r); assert(r.pre == "a*"); assert(r.post == "b"); }
Re: Supporting inout haystack in array-overload of findSplitBefore without template-bloat
On Sunday, 27 October 2019 at 14:29:01 UTC, Per Nordlöw wrote: which results in the following interesting compiler error: array_algorithm.d(506,12): Error: modify `inout` to `immutable` is not allowed inside `inout` function assert(r.pre == "a*"); ^ array_algorithm.d(507,12): Error: modify `inout` to `immutable` is not allowed inside `inout` function assert(r.post == "b"); ^ array_algorithm.d(514,5): Error: static assert: `is(typeof(r.pre()) == const(char)[])` is false static assert(is(typeof(r.pre()) == const(char)[])); A non-templated and less bloated but still suboptimal solution is to defined inlined overloads for the member functions, this case `pre()`: auto findSplitAfter_inout(T)(scope inout(T)[] haystack, scope const T needle) @trusted { static struct Result { private T[] _haystack; private size_t _offset; auto pre() @trusted { pragma(inline, true); if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[0 .. _offset + 1]; } auto pre() const @trusted { pragma(inline, true); if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[0 .. _offset + 1]; } auto pre() immutable @trusted { pragma(inline, true); if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[0 .. _offset + 1]; } auto post() const @trusted { if (_isMiss) { return _haystack[0 .. $]; } return _haystack.ptr[_offset + 1 .. _haystack.length]; } bool opCast(T : bool)() const { return !_isMiss; } private bool _isMiss() const { return _haystack.length == _offset; } } foreach (const offset, const ref e; haystack) { if (e == needle) { return inout(Result)(haystack, offset); } } return inout(Result)(haystack, haystack.length); } /// @safe pure nothrow @nogc unittest { auto r = "a*b".findSplitAfter_inout('*'); static assert(is(typeof(r.pre()) == string)); assert(r); assert(r.pre == "a*"); assert(r.post == "b"); }
Re: Using a char value >= 128
On Sunday, 27 October 2019 at 14:36:54 UTC, Ernesto Castellotti wrote: On Sunday, 27 October 2019 at 12:44:05 UTC, Per Nordlöw wrote: [...] char in D is always unsigned, it is not implementation-specific. Therefore it can take values up to (2^8)−1, If you want a signed 8 byte type you can use ubyte, which obviously can take up from -(2^7) to (2^7)-1 signed 8 byte correction: they are obviously 8 bits, not 8 byte
Re: Using a char value >= 128
On Sunday, 27 October 2019 at 12:44:05 UTC, Per Nordlöw wrote: In which circumstances can a `char` be initialized a non-7-bit value (>= 128)? Is it possible only in non-@safe code? And, if so, what will be the result of casting such a value to `dchar`? Will that result in an exception or will it interpret the `char` using a 8-bit character encoding? I'm asking because I'm pondering about how to specialize the non-7-bit `needle`-case of the following array-overload of `startsWith` when `T` is `char`: bool startsWith(T)(scope const(T)[] haystack, scope const T needle) { static if (is(T : char)) { assert(needle < 128); } // TODO convert needle to `char[]` and call itself if (haystack.length >= 1) { return haystack[0] == needle; } return false; } char in D is always unsigned, it is not implementation-specific. Therefore it can take values up to (2^8)−1, If you want a signed 8 byte type you can use ubyte, which obviously can take up from -(2^7) to (2^7)-1
Supporting inout haystack in array-overload of findSplitBefore without template-bloat
Is it possible to make this array-overload of findSplitBefore support `inout`-qualified `haystack` parameter and return type without using a templated `Result`? auto findSplitBefore(T)(scope const T[] haystack, // TODO support inout? scope const T needle) { struct Result { private alias Haystack = typeof(haystack); private Haystack _haystack; private size_t _offset; inout(Haystack) pre() inout @trusted { return _haystack.ptr[0 .. _offset]; } inout(Haystack) post() inout @trusted { if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[_offset .. _haystack.length]; } bool opCast(T : bool)() const { return !_isMiss; } private bool _isMiss() const { return _haystack.length == _offset; } } foreach (const offset, const ref e; haystack) { if (e == needle) { return Result(haystack, offset); } } return Result(haystack, haystack.length); } /// @safe pure nothrow @nogc unittest { const r = "a*b".findSplitBefore('*'); assert(r); assert(r.pre == "a"); assert(r.post == "*b"); } This is my attempt so far auto findSplitAfter(T)(scope inout(T)[] haystack, // TODO support inout? scope const T needle) @trusted { struct Result { private T[] _haystack; private size_t _offset; inout(T)[] pre() inout @trusted { if (_isMiss) { return _haystack[$ .. $]; } return _haystack.ptr[0 .. _offset + 1]; } inout(T)[] post() inout @trusted { if (_isMiss) { return _haystack[0 .. $]; } return _haystack.ptr[_offset + 1 .. _haystack.length]; } bool opCast(T : bool)() const @trusted { return !_isMiss; } private bool _isMiss() const @trusted { return _haystack.length == _offset; } } foreach (const offset, const ref e; haystack) { if (e == needle) { return inout(Result)(haystack, offset); } } return inout(Result)(haystack, haystack.length); } /// @safe pure nothrow @nogc unittest { const r = "a*b".findSplitAfter('*'); assert(r); assert(r.pre == "a*"); assert(r.post == "b"); } which results in the following interesting compiler error: array_algorithm.d(506,12): Error: modify `inout` to `immutable` is not allowed inside `inout` function assert(r.pre == "a*"); ^ array_algorithm.d(507,12): Error: modify `inout` to `immutable` is not allowed inside `inout` function assert(r.post == "b"); ^ array_algorithm.d(514,5): Error: static assert: `is(typeof(r.pre()) == const(char)[])` is false static assert(is(typeof(r.pre()) == const(char)[]));
Re: Using a char value >= 128
On Sunday, 27 October 2019 at 12:44:05 UTC, Per Nordlöw wrote: In which circumstances can a `char` be initialized a non-7-bit value (>= 128)? Is it possible only in non-@safe code? All circumstances, `char`'s default initializer is 255. char a; // is 255 And, if so, what will be the result of casting such a value to `dchar`? Will that result in an exception or will it interpret the `char` using a 8-bit character encoding? It will treat the numeric value as a Unicode code point then. I'm asking because I'm pondering about how to specialize the non-7-bit `needle`-case of the following array-overload of `startsWith` when `T` is `char`: I'd say that is just plain invalid and it should throw; I'm of the opinion the assert there is correct. But you could also do cast into dchar, then call std.utf.encode http://dpldocs.info/experimental-docs/std.utf.encode.1.html to get it back to utf-8 and compare the values then. It'd spit out a two byte pair that is probably the closest thing to what the user intended. But I'm just not convinced the library should be guessing what the user intended to begin with.
Using a char value >= 128
In which circumstances can a `char` be initialized a non-7-bit value (>= 128)? Is it possible only in non-@safe code? And, if so, what will be the result of casting such a value to `dchar`? Will that result in an exception or will it interpret the `char` using a 8-bit character encoding? I'm asking because I'm pondering about how to specialize the non-7-bit `needle`-case of the following array-overload of `startsWith` when `T` is `char`: bool startsWith(T)(scope const(T)[] haystack, scope const T needle) { static if (is(T : char)) { assert(needle < 128); } // TODO convert needle to `char[]` and call itself if (haystack.length >= 1) { return haystack[0] == needle; } return false; }