# Copy initialization: how has it changed?

**URL:** <https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814>\
**Category:** Users\
**Created:** [May 19, 2025, 9:54pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814 "2025-05-19T21:54:33Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![nelsonluisdias](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/nelsonluisdias/32/691_2.png) [@nelsonluisdias](https://chapel.discourse.group/u/nelsonluisdias)\
**Post date:** [May 19, 2025, 9:54pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/1 "2025-05-19T21:54:33Z")

</div>

The following excerpt, coming directly from Chapel's documentation  
([Records — Chapel Documentation 2.4](https://chapel-lang.org/docs/language/spec/records.html)), does not compile (any more?):

```chapel
record MyString {
  var s : string;
}

// normal copy initializer
proc MyString.init=(other: MyString) {
  this.s = other.s;
  writeln("normal init=");
}

// initialize from a string
proc MyString.init=(other: string) {
  this.s = other;
  writeln("string init=");
}

var A = new MyString("hello");
var B = A; // "normal init="
var C : MyString = "goodbye"; // "string init="

```

and the error issued by the compiler in version 2.4 is

```Chapel
advanced.chpl:19: error: a cast creating 'MyString' from 'string' is missing
advanced.chpl:12: note: expected because init= is defined here between these two types

```

What is the correct form of doing this now? Thanks for any help,

Nelson

---

<div class="post-metadata">

**Author:** ![bradcray](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/bradcray/32/72_2.png) [@bradcray](https://chapel.discourse.group/u/bradcray)\
**Post date:** [May 19, 2025, 10:25pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/2 "2025-05-19T22:25:08Z")

</div>

Hi Nelson —

Oops, that's embarrassing. At some point we decided that if a copy  
initializer is supported between types then a cast between those  
types should be required as well, which is what the error:

```
code.chpl:19: error: a cast creating 'MyString' from 'string' is missing
code.chpl:12: note: expected because init= is defined here between these two types

```

is conveying.

The fix is to add a cast operator, for example like this:

```
operator :(x: string, type t: MyString) {
  var s: MyString = x;
  return s;
}

```

which should make things work again  
([Run – Attempt This Online](https://ato.pxeger.com/run?1=fZE9TgMxEIVFu6cYudpIsGnRrlIEaipOYDaTrCXHY40dkgVxEpo0cBXuwGmwvT-RkaB97_l9npn3z7aTFvX5_HHw25vb76svxpZ4Aw_9o2dldvBaADxLBgc1uCQ1xVtRLJdgiPdSQ0u2B2WUV1KrF-TCMrXz-yo6q5J8h1zP6iLV-k65ysEKklu5JmhHVh61KcXYnp6LxcS8cGDLtAc5_uk_qPsTmQGHWAYkiyw9MdTlaeq5Bt9bBP97mLSjixgQp1jP6A9swKW-mFkHx-BxDpaiQ60pEqN9F-x1A2HUfAPJvIcMIHZEm6cexZDPBhjuOZ51Ou8P)).

If you have the time and interest, would you mind opening a GitHub issue  
against this error? We should (a) fix the test case, (b) update the  
description, and (c) make this code in the spec testable to prevent it  
from breaking again in the future.

Thanks,  
-Brad

---

<div class="post-metadata">

**Author:** ![nelsonluisdias](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/nelsonluisdias/32/691_2.png) [@nelsonluisdias](https://chapel.discourse.group/u/nelsonluisdias)\
**Post date:** [May 19, 2025, 10:43pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/3 "2025-05-19T22:43:02Z")

</div>

Hi Brad: within my serious limitations with github 🙂 , and a little help from google, I opened an issue --- I hope I did it more or less correctly. Thanks for the prompt response! Meanwhile, adding the cast to the code made the compilation work. Since I did not include any explicit cast in the code, however, I don't really know why it works now.

Regards

Nelson

---

<div class="post-metadata">

**Author:** ![nelsonluisdias](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/nelsonluisdias/32/691_2.png) [@nelsonluisdias](https://chapel.discourse.group/u/nelsonluisdias)\
**Post date:** [May 20, 2025, 1:37pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/4 "2025-05-20T13:37:42Z")

</div>

Perhaps the need to define a cast operator can be traced back to this text in the documentation:

"If a user implements their own init= method, they must also implement an assignment operator for the same record type. Implementing one without the other will cause the compiler to issue an error. Rationale: this requirement exists to mitigate hard-to-debug problems by requiring that type authors take responsibility for both init= and = implementations, or neither implementation."

Perhaps at some point, the requirement to implement an operator = was replaced by the requirement to implement an operator : ?

---

<div class="post-metadata">

**Author:** ![lydia](https://avatars.discourse-cdn.com/v4/letter/l/34f0e0/32.png) [@lydia](https://chapel.discourse.group/u/lydia)\
**Post date:** [May 20, 2025, 4:30pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/5 "2025-05-20T16:30:20Z")

</div>

The answer to this is that the failure was due to a check in our  
compiler rather than the code necessarily relying on the operator  
itself. We do that check to ensure that types behave in a consistent  
manner - it helps avoid cases where a library designer failed to test  
behavior in that particular way of getting a new instance, leading to  
their assumptions being violated and potentially bad behavior in other  
areas of their code for their users.

Lydia

---

<div class="post-metadata">

**Author:** ![nelsonluisdias](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/nelsonluisdias/32/691_2.png) [@nelsonluisdias](https://chapel.discourse.group/u/nelsonluisdias)\
**Post date:** [May 20, 2025, 10:31pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/6 "2025-05-20T22:31:47Z")

</div>

Yes Lydia; the compiler error message makes more sense to me now.

Thanks

Nelson

---

<div class="post-metadata">

**Author:** ![bradcray](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/bradcray/32/72_2.png) [@bradcray](https://chapel.discourse.group/u/bradcray)\
**Post date:** [May 20, 2025, 10:57pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/7 "2025-05-20T22:57:41Z")

</div>

@nelsonluisdias — To build on Lydia's response, here's a rationale that I'm proposing adding in [Make spec's docs of `init=` on records testable and refresh them so they work again by bradcray · Pull Request #27251 · chapel-lang/chapel · GitHub](https://github.com/chapel-lang/chapel/pull/27251) to address the issue (both making the examples work again, and documenting and rationalizing the requirement:

> Supporting a mixed-type copy initializer provides a way  
> to convert an expression of one type (`T1`) into another (`T2`)  
> using forms like: `var myT1: T1 = myT2;`. The other common way of  
> converting types in this way is to use a cast, like `myT2: T1`, so  
> Chapel requires both operations as a means of ensuring the type author  
> makes both forms available.

Thanks again for bringing this to our attention and filing the issue,  
-Brad

---

<div class="post-metadata">

**Author:** ![nelsonluisdias](https://yyz2.discourse-cdn.com/free1/user_avatar/chapel.discourse.group/nelsonluisdias/32/691_2.png) [@nelsonluisdias](https://chapel.discourse.group/u/nelsonluisdias)\
**Post date:** [May 21, 2025, 12:19pm UTC](https://chapel.discourse.group/t/copy-initialization-how-has-it-changed/42814/8 "2025-05-21T12:19:56Z")

</div>

Hi @bradcray: I understand the rationale now. Thanks to everybody for the  
explanations.

Regards

Nelson
