<html><head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
  </head>
  <body>
    <font size="4"><font face="monospace">This is a good example of a
        "you can, but you probably shouldn't" language feature.  The
        power-to-weight ratio isn't favorable; it is a lot of new
        machinery and concept to move the ball forward a small amount. 
        And as soon as the ball is moved forward by that amount, we will
        immediately be confronted by the next thing we can't do, and the
        solutions are likely to be an increasingly complex sequence of
        worse power-to-weight ratio ideas.  (Careful observers of Java
        history might note that this phenomenon is especially evident in
        any proposal surrounding annotations.)<br>
        <br>
        As Michael K pointed out, other languages have explored more
        general, but more suitable, answers here; what you're looking
        for is a witness to conformance to a type class.  (Our friends
        in C# have pursued something similar through abstract statics;
        for various reasons, that's less of a good match for Java than
        for C#.)  This is not a small ask; its significant new
        complexity, but the power gained is much greater.  If we were to
        choose to invest in solving problems like this one, that would
        likely be the path, but this is a big lift and we have other big
        things on our plate right now.  <br>
        <br>
        As a general note, while it is fun to imagine new language
        features, language design needs to be a holistic process.  If we
        did a hundred "point" features like this, what are the chances
        that the whole would hold together?  If we did this feature,
        what other potential feature directions are we implicitly
        foreclosing on?  These are the questions we address ourselves to
        when choosing what features to consider and not.  <br>
        <br>
      </font></font><br>
    <div class="moz-cite-prefix">On 1/25/2023 2:03 AM, Red IO wrote:<br>
    </div>
    <blockquote type="cite" cite="mid:CABKyW1sDWVmLMHiaWDcuY=RT1PZcupzcgPuB1fs3xKVvVC4x7A@mail.gmail.com">
      
      <div dir="auto">
        <div dir="auto">Summary</div>
        <div dir="auto">-------</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Enable a parameterized class to constrain the
          parameterized type to be constructible with a given list of
          parameters.</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Motivation</div>
        <div dir="auto">----------</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">It is possible since JDK 8 to get a constructor
          (method) reference of an object. This allowed for the creation
          of an unknown class with a known constructor reference. But
          currently the only way to obtain such reference is at call
          site like this:</div>
        <div dir="auto"><span style="white-space:pre">  </span></div>
        <div dir="auto"><span style="white-space:pre">  </span>Box<String>
          stringBox = new Box<>(String::new);</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">It is inconvenient for the user to supply the
          the reference themselves and can confuse them as the type of
          the parameter is something like Supplier<String> which
          doesn't require the pased reference to be a constructor. </div>
        <div dir="auto">It also clutters api's like "toArray" which
          requires an IntFunction to be type safe. </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Description</div>
        <div dir="auto">-----------</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">ConstructorInterface</div>
        <div dir="auto">A ConstructorInterface is a special kind of
          interface similar to a FunctionalInterface. It also has
          similar constraints. It only allows abstract constructors and
          no other abstract methods. It can declare multiple
          constructors though. The definition of such interface would
          look similar to this:</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><span style="white-space:pre">  </span>@ConstructorInterface
          //optional validation like FunctionalInterfaces</div>
        <div dir="auto"><span style="white-space:pre">  </span>public
          interface DefaultConstructible {</div>
        <div dir="auto"><span style="white-space:pre">          </span>new();</div>
        <div dir="auto"><span style="white-space:pre">          </span>new(char[]
          chars);</div>
        <div dir="auto"><span style="white-space:pre">  </span>}</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">A parameterized type could declare this
          interface as a type bound for its parameter and therefore
          enabling it to be constructed safely. Like this:</div>
        <div dir="auto"><span style="white-space:pre">  </span>public
          class Box<E extends DefaultConstructible> {</div>
        <div dir="auto"><span style="white-space:pre">          </span>public
          Box() {</div>
        <div dir="auto"><span style="white-space:pre">                  </span>E
          newElement = new E();</div>
        <div dir="auto"><span style="white-space:pre">          </span>}</div>
        <div dir="auto"><span style="white-space:pre">  </span>}</div>
        <div dir="auto">The containing type is not forced to implement
          the ContructorInterface explicitly. It is implicitly
          implemented if the required constructor(s) is(are) present.</div>
        <div dir="auto"><span style="white-space:pre">  </span>public
          static void main(String[] args) {</div>
        <div dir="auto"><span style="white-space:pre">          </span>Box<String>
          stringBox = new Box<>(); //compiles because String has
          the required constructors.</div>
        <div dir="auto"><span style="white-space:pre">          </span>Box<java.sql.Date>
          dateBox new Box<>(); error: java.sql.Data does not
          satisfy the type bound DefaultConstructible</div>
        <div dir="auto"><span style="white-space:pre">  </span>}</div>
        <div dir="auto">The interface might not be implemented by any
          class, since it doesn't follow the inheritance rule that
          extending classes of those who implement it also implement it.
          This requirement comes from the fact that extending classes do
          not necessarily need to have the same constructor signature
          and therefore don't qualify the requirements for the
          interface. Another option would be that extending classes of
          classes that implement a constructor interface explicitly are
          also required to supply the necessary constructors.</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">class Foo implements DefaultConstructable {</div>
        <div dir="auto"><span style="white-space:pre">          </span>//both
          required by the interface </div>
        <div dir="auto"><span style="white-space:pre">          </span>public
          Foo() {} </div>
        <div dir="auto"><span style="white-space:pre">          </span>public
          Foo(char[] chars) {} </div>
        <div dir="auto">} </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">class Bar extends Foo {</div>
        <div dir="auto"><span style="white-space:pre">          </span>//the
          requirement for the required constructors is passed down. </div>
        <div dir="auto"><span style="white-space:pre">          </span>public
          Bar() {} </div>
        <div dir="auto"><span style="white-space:pre">          </span>public
          Bar(char[] chars) {} </div>
        <div dir="auto">} </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">public static <T extends Foo> T createT()
          {</div>
        <div dir="auto"><span style="white-space:pre">          </span>return new
          T();</div>
        <div dir="auto">} </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">public <T extends Foo> T wrapper() {</div>
        <div dir="auto"><span style="white-space:pre">          </span>return
          createT();</div>
        <div dir="auto">} </div>
        <div dir="auto">This would technically work but would require a
          lot of static analysis to find the real type of T to call its
          constructor. </div>
        <div dir="auto">Restricting the use of "new T()" to type
          parameters that specify a constructor interface directly and
          only allow those to be resolved with a concrete type rather
          than another type parameter. </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Alternatives</div>
        <div dir="auto">------------</div>
        <div dir="auto">An alternative would be to introduce new syntax
          to restrict the ability of certain constructors on a parameter
          type. Like c# does (but only for the default constructor) :</div>
        <div dir="auto">public static T foo<T>() where T: new() {</div>
        <div dir="auto"><span style="white-space:pre">          </span>return
          new T();</div>
        <div dir="auto">} </div>
        <div dir="auto">In java:</div>
        <div dir="auto">public static <T extends new()> T foo() {</div>
        <div dir="auto"><span style="white-space:pre">          </span>return
          new T();</div>
        <div dir="auto">} </div>
        <div dir="auto">The downside of this approach is obviously the
          introduction of new syntax rather than reusing the
          interface/inheritance syntax. </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Another alternative to this approach could be to
          implement static abstract methods. This would allow an
          interface to mandate a static Factory Method. The downside of
          this approach is that it requires the parameter class to
          actually implement the interface and the concept of type
          erasure would need to be addressed for static abstract methods
          to work. In contrast the ConstructorInterface enables every
          class that matches its contract to pass the type bound.</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Risks and Assumptions</div>
        <div dir="auto">---------------------</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">As mentioned before the restriction the
          interface is giving on a type bound is different to normal
          interfaces, it restricts by its containing abstract
          constructors not by the type itself. It also makes use of the
          new operator on type variables. </div>
        <div dir="auto"><br>
        </div>
      </div>
    </blockquote>
    <br>
  </body>
</html>