Earlier quoted context omitted.
C++ doesn't have this problem, because it doesn't allow virtual function templates. For that matter, it doesn't allow any templates across ABI boundary, except when you manually instantiate them (extern template) - and then only for those explicit instantiations. So it is effectively impossible to have a generic C++ API using templates that is not statically linked.
Of course it does, as I said I was doing that. Borland C++ for Windows 3.x had an initial implementation for templates as they started to be discussed at ANSI and also supported exporting classes across dlls, providing both producer and consumer were Borland C++.
What’s New in C# 7.0
251–260 of 278 posts
Re: What’s New in C# 7.0
#252Earlier quoted context omitted.
Out parameters are also useful in constructors. I often use them as a way to limit the scope in which an object can be modified, which lets me have mostly immutable objects. IEnumerable GetStudents(SqlCommand cmd) { var rdr = cmd.ExecuteReader(); //select * from student left join courses on... var memo = new Dictionary (); //Completion lets us add courses to a student while(rdr.Read()) { if(!memo.TryGetValue(rdr.GetI…
So I'm taking a look at this line: if(!memo.TryGetValue(rdr.GetInt32("student_id"), var out complete) memo.Add(new Student(rdr out complete).ID, complete); I think I understand your point, but I found this code really hard to read. You don't use the first var out complete in the TryGetValue, right? And the Student c'tor returns itself as an out parameter? If I understand you correctly, you like this because you don't…
> You don't use the first var out complete in the TryGetValue, right?
There is only one complete variable; we declare it in TryGetValue, and it's definitely used in the last line of the while statement, but might first be used after the if statement.
> And the Student c'tor returns itself as an out parameter?
The Student constructor does not return itself as an out parameter, rather it returns an object that can modify an internal list of courses.
The idea is that when we iterate through a result set from a database, some of the rows are going to correspond to a new student object, and some are going to correspond to a course that belongs to the student. Crucially, we are only allowed modify the Student object (or whatever) during iteration, and the collection that we return will only contain immutable/unmodifiable Student objects.
I've used this technique to populate deeply nested structures (lots of joins and nested joins) using only one query.
> I would rather put a simple IEnumerable in front of SqlDataReader so that you could just do:
> foreach(var row in rdr) yield return new Student(row)
Just to be clear, the reason that I cannot do that is because the Student object might not be completely "hydrated" until we finish iterating through the result set, because it might contain a bunch of nested objects that also need to be instantiated from one or more DB records.> Also, why not enforce your student ID constraint in SQL instead of putting everything in a dictionary only to take it back out again?
I'm not quite sure I understand this (which is probably my fault), but rest assured that we use nothing but SQL (specifically, DDL) to enforce data integrity.
Re: What’s New in C# 7.0
#253Earlier quoted context omitted.
Out parameters are also useful in constructors. I often use them as a way to limit the scope in which an object can be modified, which lets me have mostly immutable objects. IEnumerable GetStudents(SqlCommand cmd) { var rdr = cmd.ExecuteReader(); //select * from student left join courses on... var memo = new Dictionary (); //Completion lets us add courses to a student while(rdr.Read()) { if(!memo.TryGetValue(rdr.GetI…
So I'm taking a look at this line: if(!memo.TryGetValue(rdr.GetInt32("student_id"), var out complete) memo.Add(new Student(rdr out complete).ID, complete); I think I understand your point, but I found this code really hard to read. You don't use the first var out complete in the TryGetValue, right? And the Student c'tor returns itself as an out parameter? If I understand you correctly, you like this because you don't…
Re: What’s New in C# 7.0
#254Earlier quoted context omitted.
Did you guys look into alternative syntax for return types? It really is a huge eyesore, and impediment to reading, when you have more than just a typename and a couple of modifiers like * and [] attached to it. With tuples especially, it's even worse, because the method name gets squished between two very similarly looking ()s, which is very different from how methods have historically looked in code. If I were scan…
What would you suggest? public TResult SomeMethod() where TResult : (string name, int id)
public SomeMethod(bool b) -> (string name, int id) { ... }
However, this may be undesirable due to confusion with => for lambdas and expression-bodied methods, especially in: public SomeMethod(bool b) -> (string name, int id) => ...
: is the next obvious candidate, and would unify the syntax with TypeScript and many other languages. But given that it's already used for labels and named arguments, I'm not sure there's enough room there to reuse it also for types.:: is another decent choice in terms of familiarity coming from other languages (Fortran, Haskell etc). But, unfortunately, it's already taken for extern alias, and I don't think this could be easily disambiguated in many contexts.
Now, if this is narrowly scoped to method return type only (i.e. we're not trying to invent a syntax that could later be used in a similar way to swap the type and the name in other places, like arguments and variables), and only as a fallback for when the usual "Type Name" arrangement has poor readability, perhaps take a hint from Ada and reuse "return"?
public SomeMethod(bool b) return (string name, int id) { ... }
A tad verbose, but if it's intended to be used sparingly, primarily with tuple-returning methods and deeply nested generics, I think that's okay - tuples themselves are pretty verbose when components are named.Or maybe borrow "as" from VB? It looks like it could be extended to other kinds of declarations in the future in a straightforward manner, without conflicting with its existing use for casts:
// Just for method return types
public SomeMethod(bool b) as (string name, int id) { ... }
// For everything
public SomeMethod(b as bool) as (name as string, id as int) {
var x as float;
TryFoo(out var y as bool);
...
switch (obj) {
case foo as Foo:
...
}
}Re: What’s New in C# 7.0
#255Earlier quoted context omitted.
> CSharp once again showing it is the best language in terms of features and improvements. That's a pretty sweeping generalization. Most of the headline features in the article are already in other languages e.g. Scala.
The difference being CSharp is actually used by a large number of people. Scala is not even in the top 10 used languages [0]. [0] http://www.tiobe.com/tiobe-index/
Re: What’s New in C# 7.0
#256Earlier quoted context omitted.
>c/java style syntax is showing it's age compared to something like scala which has return type declarations at the end, which I find much more readable I hope there are better examples of Scala's syntactical advantages than this one, because it seems like the 'egyptian-style' vs 'next line style' brace bracket debate...
Yes there are plenty. The correct order of type declarations just ties in with the better syntax for generics and leads to an easier to read, more consistent language.
Re: What’s New in C# 7.0
#257Earlier quoted context omitted.
They run deterministicaly though, making them much safer. I've done migrations with these tools that would be impossible with redgate, clients could be several months out of date since an upgrade and the migrations would just work. I've seen redgate/ssdt need manual coaching after just a few weeks. I also think your over estimating the popularity of red gate. A minority of places use it, whereas a lot use EF migratio…
Literally every place I've worked uses red gate. I've never had an issue with it, If you make sure your database is constantly up to date. So changes are small.
I've had the opposite experience, I've only been at one place that used it and a couple that considered it.
> I've never had an issue with it, If you make sure your database is constantly up to date. So changes are small.
This is not an option in many places, if you have 3 month release cycles for instance (although I favor continuous deployment). Another is when you have apps installed on site, some clients can be multiple versions behind.
Re: What’s New in C# 7.0
#258Earlier quoted context omitted.
What would you suggest? public TResult SomeMethod() where TResult : (string name, int id)
The most obvious approach would be to repurpose C++ syntax, since it's already been around for a while, and C# syntax is generally pretty close to C++ in many respects. So: public SomeMethod(bool b) -> (string name, int id) { ... } However, this may be undesirable due to confusion with => for lambdas and expression-bodied methods, especially in: public SomeMethod(bool b) -> (string name, int id) => ... : is the next…
public SomeMethod(bool b) -> (string name, int id) { ... }
When was this added to c++? I think I need to brush up on my lower level skills.Re: What’s New in C# 7.0
#259Earlier quoted context omitted.
Did you ever maintain vb6 apps? Because I still want to cry thinking about the times I've had to.
I have. If they were designed well then they are normally OK to maintain. If they were developed badly then they can take extra effort. Much like any other project in any other language. If you had an large old Vb6 project build using MVP pattern you would be laughing.
Much like any other project in any other language.
Yes, you can write good or bad code in any language. But some languages have an endemic culture of not caring about good code. IME, VB is one of them, as is PHP.All the VB6 code I've seen has been a random mashup of databinding directly to the and click handling. The tools encouraged this approach.
Re: What’s New in C# 7.0
#260Earlier quoted context omitted.
The most obvious approach would be to repurpose C++ syntax, since it's already been around for a while, and C# syntax is generally pretty close to C++ in many respects. So: public SomeMethod(bool b) -> (string name, int id) { ... } However, this may be undesirable due to confusion with => for lambdas and expression-bodied methods, especially in: public SomeMethod(bool b) -> (string name, int id) => ... : is the next…
I like the as syntax, it may conflict with casting though when used on variables. public SomeMethod(bool b) -> (string name, int id) { ... } When was this added to c++? I think I need to brush up on my lower level skills.
template
auto foo(A1 a1, A2 a2) -> decltype(a1 + a2) {
return a1 + a2;
}