|
GrumpyDoctor posted:This is the problem that generics solved, but the collection you're iterating over doesn't have a generic interface, which is why var's type inference isn't working. Var's type inference is working correctly; the compiler is unable to deduce the specific type since that information was erased because of collection not exposing it.
|
# ? Sep 18, 2014 18:00 |
|
|
# ? Jun 5, 2024 03:43 |
|
Malcolm XML posted:Var's type inference is working correctly; the compiler is unable to deduce the specific type since that information was erased because of collection not exposing it. Well, okay, "working" in the "working the way they expect it" sense.
|
# ? Sep 18, 2014 18:01 |
|
Newf posted:I get that, but I don't get why I'm able to declare the type of a variable when the compiler doesn't know it ahead of time. It feels like a stricter version would force me to expect only objects from an IEnumerable and then cast them myself - at least in this case the cast becomes explicit. Basically the C#/VB languages consider foreach loops to be explicit casts. The relevant part of the C# spec is $8.4.4 quote:A foreach statement of the form The key bit is "(V)(T)e.Current".
|
# ? Sep 18, 2014 18:47 |
|
GrumpyDoctor posted:http://stackoverflow.com/questions/3917129/foreachderived-obj-in-new-listbase is your exact question with the answer (tldr it's a special thing that foreach does for historial reasons) ljw1004 posted:Basically the C#/VB languages consider foreach loops to be explicit casts. Thanks both, and all. I think at least that the quality of my confusions is rising.
|
# ? Sep 18, 2014 19:16 |
|
A Tartan Tory posted:I take it that is done in LINQ? Not overly familiar with it, but I'll take a look once I'm back at home later. Is there a way to do it with just basic loops? (edit: answering my own question after looking at it a bit further, I think I understand whats happening there, will update later if I get it to work!) Yep, that's LINQ. Take any efforts you can to learn it because the vast majority of loop constructs in your code become obsolete. That code is using .Zip and .Aggregate, which are more "advanced" LINQ operators, to evaluate the SumProduct. However, .Skip and .Take should be pretty intuitive.
|
# ? Sep 18, 2014 19:31 |
|
Bognar posted:Yep, that's LINQ. Take any efforts you can to learn it because the vast majority of loop constructs in your code become obsolete. I'll try to learn that after I learn how to clean up my code/methods then, your post really helped me finish what I was wanting to do though (I got it working!) so I really want to thank you and everyone else who was helping me, especially GrumpyDoctor! If you are interested, here is how I finally managed it. code:
|
# ? Sep 19, 2014 14:13 |
|
Right, I have one more problem and I'm hoping someone can tell my sleepy idiotic brain why the results are doing this and how to fix it because it's literally the last thing I have to fix and it's bugging me a lot now (apparently I still don't understand how the WPF binding does what it does ). Essentially, when displaying the results in a data grid, based on a checkbox boolean value of whether or not to display that particular module of the program (see Main Display in Controller), the program displays the values on separate lines like this. Is there an easy way to get them to display on the same line, depending on what has been clicked and to not display anything that hasn't been chosen? I'm kinda, sorta aware that I could do it with different bindings, but because of the way I have used methods in the code I can't really find a way to get it to work. Any help would be appreciated. Code (tried to make it as readable as possible given my terrible use of methods) is available here: http://www.filedropper.com/insval_1 A Tartan Tory fucked around with this message at 16:15 on Sep 19, 2014 |
# ? Sep 19, 2014 15:48 |
|
I'm using EF Code First with a DB my application owns (like there are no other clients and for various reasons I strongly doubt there will be any that don't use my data access library). I'm running into efficiency problems because in some places I've declared navigation properties in derived types and if you're doing queries on the supertype, you can't use the Include method to include navigation properties that only exist on subtypes. So what happens instead is you fall back to lazy loading and the database is hit every time you hit one of those properties which can be quite a few queries. You can do an OfType<> query and concatenate things together but that's messy and doesn't work too well for a lot of scenarios. I'm thinking about a couple ways I might ameliorate it, but I'm not entirely sure I'm happy with either. Is there a better way, or, if not, which of these seems better? 1. I could move the actual declaration to the base type, using some sort of naming convention to indicate that these are "private" (not really because they have to be public, but that they should be treated as private) (e.g., _Property instead of the usual Property). I could then, on the derived type, add in a "real" property and just have the getters and setters refer to the base property. I think if I do this right I can even avoid changing the DB schema. My biggest issue with this is it's going to introduce a lot of noisy boilerplate for classes with a lot of descendants. 2. I could switch to serialization, then hook into EF's materialization to deserialize, serializing again on the save event. This certainly makes it simpler (hey, don't need to include anything at all!) and I don't really need to do queries on the contents of the fields in question. But this does go against normal sound DB design so I still have misgivings (although to be fair it's not like my Code First-generated database schema is a paragon of good DB design either). (There's obviously the option of ditching EF but at that point I'd sooner just live with the problem because it would be a ton of work)
|
# ? Sep 20, 2014 03:01 |
|
Can you lay out an example of the tables & entity classes you have and the queries you are attempting to run? The description is a bit hard to understand.
|
# ? Sep 20, 2014 11:50 |
|
EssOEss posted:Can you lay out an example of the tables & entity classes you have and the queries you are attempting to run? The description is a bit hard to understand. code:
code:
So because of that I'd like to change things in such a way that an include is unnecessary to avoid another query.
|
# ? Sep 20, 2014 18:39 |
|
RICHUNCLEPENNYBAGS posted:.. Eager loading of derived types does not appear to be supported, nor are they even working on it. http://data.uservoice.com/forums/72025-entity-framework-feature-suggestions/suggestions/1249289-include-property-of-derived-classes I can't think of a solution that isn't a huge pain. Refactor your entity model so that it doesn't use inheritance (I know, this is also a huge pain)?
|
# ? Sep 21, 2014 00:39 |
|
Che Delilas posted:Eager loading of derived types does not appear to be supported, nor are they even working on it. Did you see my previous post? I had two possible solutions in mind, one of which was sort of that.
|
# ? Sep 21, 2014 00:59 |
|
edit: Nevermind, that didn't really make sense overall. Does EF work properly with interfaces? So instead of using the abstract BaseClass, you could just compose your derived classes by implementing various interfaces, then maybe use some master interface from the context to add the query conditions? Silvah fucked around with this message at 04:17 on Sep 21, 2014 |
# ? Sep 21, 2014 03:28 |
|
I tried using a subclassing structure for modeling my database once and I will never try it again. This is just one of the headaches you will encounter. My recommendation is to not try to make any fancy entity model - just treat your entity classes as database rows and you'll have a happy life.
|
# ? Sep 21, 2014 12:41 |
|
Silvah posted:Does EF work properly with interfaces? So instead of using the abstract BaseClass, you could just compose your derived classes by implementing various interfaces, then maybe use some master interface from the context to add the query conditions? EssOEss posted:I tried using a subclassing structure for modeling my database once and I will never try it again. This is just one of the headaches you will encounter. My recommendation is to not try to make any fancy entity model - just treat your entity classes as database rows and you'll have a happy life. This sounds more or less exactly like what I'm currently attempting to do. I'm working on a math-tutoring app that's got a pile of different question classes which have a shared inheritance structure blah blah. It's code-first with the current MVC5 / EF6 / VS2013. Haven't run into any problems yet but I'm always nervous that I might sneeze in the wrong direction and then my program will never compile again.
|
# ? Sep 21, 2014 13:27 |
|
EssOEss posted:I tried using a subclassing structure for modeling my database once and I will never try it again. This is just one of the headaches you will encounter. My recommendation is to not try to make any fancy entity model - just treat your entity classes as database rows and you'll have a happy life. I don't necessarily disagree with this but I'm on version 3 of this application and I'm not gonna change it now.
|
# ? Sep 21, 2014 17:34 |
|
Silvah posted:edit: Nevermind, that didn't really make sense overall. Using interfaces is actually a decent way to handle this. Your entity model would look something like this: C# code:
|
# ? Sep 22, 2014 14:20 |
|
EssOEss posted:I tried using a subclassing structure for modeling my database once and I will never try it again. This is just one of the headaches you will encounter. My recommendation is to not try to make any fancy entity model - just treat your entity classes as database rows and you'll have a happy life. Inheritance is usually bad and this is one of many reasons why. There are some scenarios where an open or quasi-open schema would work better than straight inheritance. Then, you expose your entities as views. The views give you a little bit more abstraction between your tables and your database code. I don't really bother with EF (or most other ORM like it) anymore. I feel like EF is a trap that lulls you into using a bunch of weird inheritance, and you end up spending more time tweaking queries and includes than you would've just creating a set of repository classes that wrap SQL calls.
|
# ? Sep 23, 2014 19:17 |
|
RangerAce posted:Inheritance is usually bad and this is one of many reasons why. There are some scenarios where an open or quasi-open schema would work better than straight inheritance. Then, you expose your entities as views. The views give you a little bit more abstraction between your tables and your database code. Inheritance is "usually bad?" Like, not just in ORMs but in general design? Seems like an overly reductive way of programming to me. I don't agree on the ORM front. Sure, making it run efficiently takes some effort, but 1) it is very easy to get it running correctly, without worrying about performance at all (which can matter if you had to just get something out the door first) 2) tuning the performance is still much easier than writing all the SQL to do equivalent things for some of the more complex things you can ask for. Besides that EF (or any provider that implements LINQ) lets you build up an expression dynamically (with the various classes that inherit Expression) and then use that same expression either on a database or on an expression that exists in-memory which is insanely cool and useful if you want to offer, say, a reporting function.
|
# ? Sep 24, 2014 02:55 |
|
RICHUNCLEPENNYBAGS posted:Inheritance is "usually bad?" Like, not just in ORMs but in general design? Seems like an overly reductive way of programming to me. I find using in-line SQL (with wrapper class as RangerAce stated) to return an IEnumerable<DataRow> with the additional flexibility of LINQ to be incredibly powerful. Each query language is better at something and when combined complex queries become easier to write.
|
# ? Sep 24, 2014 04:24 |
|
If it works for you I'm not going to knock it but some of the scorn directed at ORMs doesn't make a lot of sense to me. Like, yeah, they're slow, but "my application is so popular and otherwise performant that the speed of the ORM is a real issue" is like, a nice problem to have and one many of us don't.
|
# ? Sep 24, 2014 04:51 |
|
In my opinion the best things about Entity Framework are code-first database generation, migrations, expression/IQueryable support, and change tracking. These make it very easy to work with both in rapid prototyping on greenfield projects and in maintenance on older projects. However, none of these things are unique to EF - many other .NET ORMs have the same feature set. All other things equal, I would stick with EF over other ORMs simply because it's Microsoft's baby right now and they'll be supporting it for at least a while, as well as coordinating releases with framework updates (e.g. await/async support). Code first database generation with migrations really is wonderful. Most of the time when modifying the structure of a database you're doing stupid simple stuff like adding tables, columns, or indexes - things that are not complicated and are mostly boilerplate that you're having to add to support your object model. With migrations, you just modify your model, tell Visual Studio to diff it to figure out what changed, then generate a simple code file describing the changes. You just type in add-migration MyStupidChanges in the Package Manager Console and all the work is done for you. This makes rapid prototyping a breeze. If you have the need to do something more complex like move data around or apply calculations to new columns, you can always modify the migration and add custom SQL. Expressions and IQueryable support are par for the course with most ORMs, but the composability of Expressions gives a very nice way of building queries. In our own applications at work, we have used Expressions in numerous powerful ways to generalize common query operations and reduce code complexity. However, with all this power you can easily shoot yourself in the foot (e.g. exposing IQueryables outside of your data layer, you do have a data layer right?). RangerAce posted:I don't really bother with EF (or most other ORM like it) anymore. I feel like EF is a trap that lulls you into using a bunch of weird inheritance, and you end up spending more time tweaking queries and includes than you would've just creating a set of repository classes that wrap SQL calls. Most ORMs tend to fall apart when you start trying to map an inheritance hierarchy onto them. Sure, it's kind of supported but you always run into edge cases. If you just have data objects that closely map to the DB table structure with object navigation properties for foreign key relationships, you can go extremely far with EF. Given that, I don't understand how EF lulls you into using inheritance. It's a minor feature with poor support (as evidenced by the above posts). When dealing with SQL in .NET it comes to three things: 1. Full-fledged ORM - use this to handle all your CRUD, drop back to SQL as necessary for complex interactions or efficiency. If you choose this, I would always recommend EF for the reasons above. 2. Micro-ORM - write your own SQL and quickly map to and from objects. This is good if you absolutely need the performance, or if you just really like SQL and are scared of the big bad ORM. If you choose this, I would always recommend Dapper (because it's fast, that's why you picked a micro-ORM right?). This can also be a good choice if you are refactoring a legacy application with handwritten/inline SQL. 3. Raw SQL connections - For pure speed and pure speed only. Honestly, I would never recommend this considering how fast libraries like Dapper are. If you're at the point where the performance difference of mapping to an object matters, you should probably consider a different language entirely. fake edit: This turned into a much longer post than I expected and is probably rambling in places.
|
# ? Sep 24, 2014 05:31 |
|
OK, I'm feeling in a heretical mood, so I'm going to go ahead and bite on this: is it really morally superior to have a whole separate data layer that looks up an object by ID rather than to have context.SomeDbSet.Find(id)? What's it giving you?
|
# ? Sep 24, 2014 05:54 |
|
RICHUNCLEPENNYBAGS posted:OK, I'm feeling in a heretical mood, so I'm going to go ahead and bite on this: is it really morally superior to have a whole separate data layer that looks up an object by ID rather than to have context.SomeDbSet.Find(id)? What's it giving you? Assuming this is for a model that doesn't consist only of single-table entities, one advantage is not having to write a litany of .Include(property) calls every time you want to get a complex object without triggering the N+1 select problem.
|
# ? Sep 24, 2014 13:11 |
|
RICHUNCLEPENNYBAGS posted:OK, I'm feeling in a heretical mood, so I'm going to go ahead and bite on this: is it really morally superior to have a whole separate data layer that looks up an object by ID rather than to have context.SomeDbSet.Find(id)? What's it giving you? Well, for one, it makes it much easier to unit test if you're calling an injected interface method that returns your data rather than calling a method on a concrete ORM DB object. Another benefit is that all of your queries live in one project, so if you have to refactor something in your data, you're not changing things over your entire solution. Also, if for some reason you need to drop down to SQL instead of using the ORM (e.g. for performance), you can do so in that one method without having to touch the calling code.
|
# ? Sep 24, 2014 13:40 |
|
Absolutely -- no matter what data back end we are using (mainly ravendb these days, with some EF and micro orms as required) we keep it sequestered in some sort of data access service layer. The upper layers should not know about anything horribly database specific.
|
# ? Sep 24, 2014 13:41 |
|
I use NHibernates ISession directly in the controllers. It's awesome!
|
# ? Sep 24, 2014 15:09 |
|
Bognar posted:In our own applications at work, we have used Expressions in numerous powerful ways to generalize common query operations and reduce code complexity. Care to share any examples of this? These always interest me.
|
# ? Sep 24, 2014 16:15 |
|
Kind of running tight here, hoping someone can help with the answer. Using WPF I'm trying to bind a combobox value (hardcoded items) to a property in my viewmodel.model. XAML: XML code:
XML code:
Thanks in advance.
|
# ? Sep 24, 2014 19:46 |
|
Knyteguy posted:Using WPF I'm trying to bind a combobox value (hardcoded items) to a property in my viewmodel.model. This might be what you're looking for XML code:
epswing fucked around with this message at 20:40 on Sep 24, 2014 |
# ? Sep 24, 2014 20:22 |
|
Opulent Ceremony posted:Care to share any examples of this? These always interest me. I'll start with one of the most complicated examples, mainly because I think it's really cool. One of the applications we're developing is very enterprisey in its requirements and as part of that they want every action to be tracked for reporting at multiple levels. For example, consider the following hierarchy: code:
Now, some background on another internal framework is required. One of our developers put together a type-safe system of defining relationships between objects. There is a lot of voodoo compiler magic with generics and extension methods behind the scenes to make this work, but that is all to make using it easier. It allows you to do define a relationship like this: C# code:
C# code:
All of our updates pass through a base repository that actually interacts with EF to apply the changes. All of our updates are described before that using a Delta<T> class (not the OWIN one, a custom-rolled version) that has an Id of the object to apply changes to and a list of the changes that should be applied. I can go into this in a separate post if you want details. The base repository that executes the updates loads the object in, but it also uses .IncludeIfSupported() to load in relationships for ChangeTrackedItem.Relation, ChangedTrackedItemSet.Relation, ChangeTrackedTeam.Relation, and ChangeTrackedCompany.Relation. If those relationships exist, then it creates an action item and indicates that whatever entities that were supported in those relations had changes. How this would play out in the above example, is that we describe a set of changes to Item 1 and call Update. Item 1 is loaded in joined with its Item Set, Team, and Company. In the log of actions taken, it is noted that this action modified an item under that specific Item Set, Team, and Company. When viewing that log, you can just filter on the Id and Type of changes to view everything that happened at each level. The big benefit of all this is when you add an entity to the model that should have its changes tracked. All you have to do is write one expression saying how to get from that item to the Company/Team/whatever and the changes are tracked automatically. I was worried when building this, as I constantly am, about the performance implications of using a solution like this that does a significant amount of magically loading in extra entities. However, we have benchmarked it in multiple situations and only seen a 5-15% decrease in performance. I'm sure it could get significantly worse if you are joining on the entirety of your object model, but in the ways we use it I've seen no reason to expect that it will cripple the system. Bognar fucked around with this message at 23:20 on Sep 24, 2014 |
# ? Sep 24, 2014 23:14 |
|
I appreciate you taking the time to write all that out! Very neat stuff (that I'm going to need to re-read a couple times).
|
# ? Sep 25, 2014 00:30 |
|
Funking Giblet posted:I use NHibernates ISession directly in the controllers. Do you get paid by the hour?
|
# ? Sep 25, 2014 08:10 |
|
Bognar posted:Enterprisey stuff
|
# ? Sep 25, 2014 08:22 |
|
ORMs are kinda nice in that they allow you to do some complex querying using higher-level query syntax, but that's honestly about it. They infiltrate the design of your domain and once you're at any kind of scale at all you'll be looking at a ORM profiling tool to figure out why the hell it's generating N+1 queries. Not to mention the fact that usually you can only map your domain in one way whereas you may want to have different mappings depending on the type of query.
|
# ? Sep 25, 2014 10:15 |
|
wwb posted:Do you get paid by the hour? It works quite well, The session is already an abstraction. I use query objects and extension methods to help out here and there, but otherwise I just pull the data I need.
|
# ? Sep 25, 2014 11:35 |
|
mortarr posted:That's some serious business... Can you go into how you end up building something like that, like how did you choose EF, how long did it take to design and put together, what's your team size etc. Assuming you're allowed to discuss that? Sure. The decision to use Entity Framework didn't involve too much thought. It's kind of a baseline for most projects here and we tend to stick with it unless the project calls for something other than a relational data store. As part of that, we've come up with a standard base repository class that works for most projects. I'll try to re-create it from memory here: C# code:
C# code:
All of the above is fairly standard for our projects. The pieces specific to this project are how we applied the Relationship system to implement change tracking. Because we have the BaseRepository<T> class, we can make changes that affect every database interaction in the project. Once we actually had the idea of combining the two systems for change tracking, it wasn't more than a day or two to fully implement, test, and benchmark. On the other hand, the Relationship system is an ongoing experiment on this project to see how it works out. We brought it in at the beginning and have been slowly shaping it over the course of the past three months as we found new uses or possible features. Our team sizes in general are small. Usually around 2-3 people per project. Everyone is expected to understand the full stack from the DB to the UI, which is kind of important at those small sizes.
|
# ? Sep 25, 2014 13:53 |
|
Bognar posted:Well, for one, it makes it much easier to unit test if you're calling an injected interface method that returns your data rather than calling a method on a concrete ORM DB object. Another benefit is that all of your queries live in one project, so if you have to refactor something in your data, you're not changing things over your entire solution. Also, if for some reason you need to drop down to SQL instead of using the ORM (e.g. for performance), you can do so in that one method without having to touch the calling code. Why not just mock the repository itself? That's the approach I'm using... an IRepository class that's a very thin layer over DbContext so I can switch it out in tests. That doesn't answer the other benefits you have mentioned though, and certainly the Include thing is good too (although the problem is what needs to be included is kind of consumer-specific). RICHUNCLEPENNYBAGS fucked around with this message at 14:11 on Sep 25, 2014 |
# ? Sep 25, 2014 14:09 |
|
RICHUNCLEPENNYBAGS posted:Why not just mock the repository itself? That's the approach I'm using... an IRepository class that's a very thin layer over DbContext so I can switch it out in tests. I've seen both approaches, I prefer Bognar's approach. Basically, making the repository more general shields you from the pain of swapping out ORMs later. Microsoft might scrap EF the way they scrapped LINQ to SQL (although it's admittedly unlikely). It also shields consumers from the inner workings of the ORM.
|
# ? Sep 25, 2014 14:13 |
|
|
# ? Jun 5, 2024 03:43 |
|
I suppose that's reasonable although the price you pay is more code upfront.
|
# ? Sep 25, 2014 15:47 |