digitalmars.D.learn - opIndex operators
- gedaiu (21/21) Apr 13 2013 Hi again!
- bearophile (63/76) Apr 13 2013 opIndex returns the value contained in the "array", while
- gedaiu (8/8) Apr 13 2013 Hi,
- bearophile (29/34) Apr 13 2013 Instead of returning float as in my case, you return something
- gedaiu (15/50) Apr 13 2013 Value[Value] container;
- bearophile (6/19) Apr 14 2013 When possible it's better to show the actual code, and
- Jesse Phillips (7/15) Apr 14 2013 void foo(Value v);
Hi again! I don't understand why we have opIndex() and opIndexAssign()... can anyone explain this for me? Because in c++ there is only one operator overload for "[]" and it looks like this: Value& Value::operator[] (constValue offset) { return container[offset]; } and with this operator overload I can set or get values from container, and also easily implement custom multilevel arrays. In D when I have this method Value& opIndex(Value index) { return container[index]; } I get this error. Error: no identifier for declarator Value Error: semicolon expected, not '&' Declaration expected, not '&' And also, how you can implement custom structs that acts like a multilevel array in D like in c++? Thanks!
Apr 13 2013
On Saturday, 13 April 2013 at 09:53:01 UTC, gedaiu wrote:Hi again! I don't understand why we have opIndex() and opIndexAssign()... can anyone explain this for me?opIndex returns the value contained in the "array", while opIndexAssign does the opposite, it puts in your "array" the given value. If you use opIndex and return the item by reference you sometimes don't need opIndexAssign. But for other cases you need both. Info on D operator overloading: http://dlang.org/operatoroverloading.htmlIn D when I have this method Value& opIndex(Value index) { return container[index]; } I get this error. Error: no identifier for declarator Value Error: semicolon expected, not '&' Declaration expected, not '&'In D there isn't that & syntax. We have "ref". But it's not usable in all the situations where you use & in C++.And also, how you can implement custom structs that acts like a multilevel array in D like in c++?By multi-level array I think you mean something like a matrix: import std.stdio; struct Foo { float[] mat; size_t nCols; this(in size_t r, in size_t c) pure nothrow in { // pre-condition assert(r > 0); assert(c > 0); } body { nCols = c; mat.length = r * c; // All NaN. } float opIndex(in size_t r, in size_t c) pure nothrow { return mat[r * nCols + c]; } float opIndexAssign(in float value, in size_t r, in size_t c) pure nothrow { mat[r * nCols + c] = value; return value; } } void main() { auto m = Foo(3, 5); m[1, 3] = 5.5; m[1, 3].writeln; m.mat.writeln; } An alternative design is to use ref. Here it can be used: import std.stdio; struct Foo { float[] mat; size_t nCols; this(in size_t r, in size_t c) pure nothrow in { assert(r > 0); assert(c > 0); } body { nCols = c; mat.length = r * c; // All NaN. } ref float opIndex(in size_t r, in size_t c) pure nothrow { return mat[r * nCols + c]; } } void main() { auto m = Foo(3, 5); m[1, 3] = 5.5; m[1, 3].writeln; m.mat.writeln; } Bye, bearophile
Apr 13 2013
Hi, thanks for the answer, but it's not the solution what i was expectig. What i want to create, is an array structure like the one from PHP where array levels are not fixed and the sintax to access rhe values is val[][] so returning a reference to a struct that have the same type as the current type is useful. there is a way to do this in D? thanks!
Apr 13 2013
gedaiu:What i want to create, is an array structure like the one from PHP where array levels are not fixed and the sintax to access rhe values is val[][] so returning a reference to a struct that have the same type as the current type is useful. there is a way to do this in D?Instead of returning float as in my case, you return something else that has opIndex and opIndexAssign. This way you can pile up the []: import std.stdio; struct Foo { ref Foo opIndex(in size_t i) { writeln("opIndex: ", i); return this; } void opIndexAssign(in float value, in size_t i) { writeln("opIndexAssign: ", value, " ", i); } } void main() { Foo f; f[1] = 2; f[3][4] = 5; f[6][7][8] = 9; } That outputs: opIndexAssign: 2 1 opIndex: 3 opIndexAssign: 5 4 opIndex: 6 opIndex: 7 opIndexAssign: 9 8 Bye, bearophile
Apr 13 2013
On Saturday, 13 April 2013 at 11:41:02 UTC, bearophile wrote:gedaiu:Value[Value] container; ref Value opIndex(Value index) { return container[index]; } why I get this error? Error: function base.Value.Value.opIndex (Value index) is not callable using argument types (string) Error: cannot implicitly convert expression ("string") of type string to Value I have implemented this methods: this(string) Value opCast(string val) Value opAssign(ref const string val) Thanks!What i want to create, is an array structure like the one from PHP where array levels are not fixed and the sintax to access rhe values is val[][] so returning a reference to a struct that have the same type as the current type is useful. there is a way to do this in D?Instead of returning float as in my case, you return something else that has opIndex and opIndexAssign. This way you can pile up the []: import std.stdio; struct Foo { ref Foo opIndex(in size_t i) { writeln("opIndex: ", i); return this; } void opIndexAssign(in float value, in size_t i) { writeln("opIndexAssign: ", value, " ", i); } } void main() { Foo f; f[1] = 2; f[3][4] = 5; f[6][7][8] = 9; } That outputs: opIndexAssign: 2 1 opIndex: 3 opIndexAssign: 5 4 opIndex: 6 opIndex: 7 opIndexAssign: 9 8 Bye, bearophile
Apr 13 2013
gedaiu:Value[Value] container; ref Value opIndex(Value index) { return container[index]; } why I get this error? Error: function base.Value.Value.opIndex (Value index) is not callable using argument types (string) Error: cannot implicitly convert expression ("string") of type string to Value I have implemented this methods: this(string) Value opCast(string val) Value opAssign(ref const string val)When possible it's better to show the actual code, and double-bonus if it's complete and compilable (or supposed to be compilable). Bye, bearophile
Apr 14 2013
On Sunday, 14 April 2013 at 06:57:34 UTC, gedaiu wrote:Error: function base.Value.Value.opIndex (Value index) is not callable using argument types (string) Error: cannot implicitly convert expression ("string") of type string to Value I have implemented this methods: this(string) Value opCast(string val) Value opAssign(ref const string val)void foo(Value v); foo("my value?"); This code does not compile unless Value is defined as alias Value = string; You'd call it: foo(Value("my value"));
Apr 14 2013