I am new to C#. Come from the C/C++ environment. My application has a List<Model> which is required all over the place, by different classes. The problem is that a copy will not do because this statement:
dataGrid.ItemsSource = myModelList;
requires the original by address. I tried changing some arguments around and passing that particular variable as ref but as soon as it is assigned with an equal sign, I end up with a copy. Correct?
You could make it a singleton.
However a concrete List needed all over the place would make me have a serious think about my design.
At the very least you should consider writing a class to control access to the list (add, remove, clear etc), and making that "global", otherwise you are going to be in deep in the brown stuff, until it hits the fan.
Create a Public Class and have the content you wish to pass declared static within the class. Then just access it as NameOfClass.NameOfMethod()
public class NameOfClass
{
public static RETURNTYPE NameOfMethod()
{
// Your Code
}
}
You can create a public class for it with a public static List inside it. That one you then can access everywhere.
eg
public class FakeGlobal
{
public static List<Model> MyModelList = new List<Model>();
}
or even make it a property with getter/setter.
Related
I 've just started writing a little app. I made things work now I am in plan to do everything what is needed better. I've discovered one mistake.
I have a class with static field which is an arraylist and its access is public.
Other classes uses it and I m wondering what would be the best option to get acces from other classes to this field.
First what I have in mind its just getter returning this list.
But I have no other ideas what could beanother option I decided to ask.
Greetings,
Betty
It can be done in a different ways, this is one of them:
public class TestService
{
private static readonly List<string> list = new List<string>();
public IEnumerable<string> List
{
get { return list; }
}
//list manipulation methods...
}
Basically, you should prevent manipulation (i.e. add/update/remove items) on that list from outside of the class. Mainly because that class should be only responsible for direct list manipulation.
So, that's the reason behind IEnumerable<string> type. Do not misuse List<string> casting on this property!
Now when you are sure that list can't be directly manipulated from the outside of the class, you should expose public methods inside TestService class. Each method should only have one responsibility and reason to change (SRP), in other words, you should have separate methods for adding, updating and removing items.
I have a 3 tier application setup like so with a console presentation layer. In my business logic I have a class where I declare a number of different variables that are fixed i.e. the values won't change. The values of these variables are taken from app settings.
Now the problem I'm finding is that my class calls off to different methods where these variables are being passed around via the method signatures. Is this good practice? If not, would it not be better using constants instead? If so, where should the constants live so I can access them where ever I need them rather than passing variables around?
EDIT
Adding some code for you guys. So they're global variables I am referring to here.
OK so in my console app (presentation), I currently have something like this:
public class Program
{
public static void Main(string[] args)
{
MainClass myClass = new MainClass(appSetting1, appSetting2, appSetting3);
}
}
Then in MainClass I have:
public class MainClass
{
private string _appSetting1 = string.Empty;
private string _appSetting2 = string.Empty;
private string _appSetting3 = string.Empty;
public MainClass(string appSetting1, string appSetting2, string appSetting3)
{
_appSetting1 = appSetting1;
_appSetting2 = appSetting2;
_appSetting3 = appSetting3;
}
public void MyMethod()
{
Method2(_appSetting1, _appSetting2);
Method3(_appSetting2, _appSetting3);
Method4(_appSetting1, _appSetting3);
}
}
I hope you can see what I mean. I'm finding myself passing around global variables across multiple methods. I just thought there would be an easier way of doing this? Such as creating a constants class or something on the lines of that? I'm not 100% sure of the best approach to go for.
In my MainClass I could just declare my global variables like this:
private string _appSetting1 = ConfigurationManager.AppSettings["appsetting1"];
private string _appSetting2 = ConfigurationManager.AppSettings["appsetting2"];
private string _appSetting3 = ConfigurationManager.AppSettings["appsetting3"];
But do I really want to be doing that in my business logic?
Another possibility is to create a Settings class that loads them and exposes them as public readonly. This has worked well for me in the past:
public class Settings
{
public static readonly string AppSetting1;
public static readonly string AppSetting2;
public static readonly string AppSetting3;
static Settings()
{
AppSetting1 = ConfigurationManager.AppSettings["appsetting1"];
AppSetting2 = ConfigurationManager.AppSettings["appsetting2"];
AppSetting3 = ConfigurationManager.AppSettings["appsetting3"];
}
}
The static constructor is called automatically before the first access to any of the variables, so you don't have to call it explicitly. Your program can access the variables as Settings.AppSetting1, etc.
I am of the config-free mindset.
If these things presumably don't change, then have an assembly that projects can reference that return the values.
I shy away from configuration files. I realise they are needed in deployment circumstances, but given that your requirement, I'd recommend a common class library that everything else can use and reference.
If you do have to change something supposedly constant, you change it in one place.
if they are in the app.config and shouldn't change you should always reference them from there rather than passing them as parameters. This way your intention that they are static values is clear in the code.
EDIT
Jims answer makes sense in that case. Its really just a short hand so instead of writing ConfigurationManager.AppSettings["appsetting1"]; you use Settings.AppSetting1. either way you would be repeating yourself if you declare them at the top every class into class level variables. I like Jim's answer better than mine though as you can extend it. I keep all config in the db and then use a singleton which has a proc call in the private instance constructor to load config. Jims answer could implement this later without you needing to change your calling code. Generally config files are a pain.
We have a Student class in our business model. something struck me as strange, if we are manipulating one student from another student, the students private members are visible, why is this?
class Program {
static void Main(string[] args) {
Student s1 = new Student();
Student s2 = new Student();
s1.SeePrivatePropertiesAndFields(s2);
}
}
public class Student {
private String _studentsPrivateField;
public Student() {
_studentsPrivateField = DateTime.Now.Ticks.ToString();
}
public void SeePrivatePropertiesAndFields(Student anotherStudent) {
//this seems like these should be private, even from the same class as it is a different instantiation
Console.WriteLine(anotherStudent._studentsPrivateField);
}
}
Can i have some thoughts on the design considerations/implications of this. It seems that you can't hide information from your siblings. Is there a way to mark a field or member as hidden from other instances of the same class?
There's an easy way to ensure this:
Don't mess around with private members of other instances of the same class.
Seriously - you're the one writing the Student code.
The easiest way to ensure this is to program to an interface, such as:
class Program
{
static void Main(string[] args)
{
IStudent s1 = new Student();
IStudent s2 = new Student();
s1.ExamineStudentsMembers(s1);
}
}
public interface IStudent
{
void ExamineStudentsMembers(IStudent anotherStudent);
}
public class Student : IStudent
{
private string _studentsPrivateMember;
public Student()
{
_studentsPrivateMember = DateTime.Now.Ticks.ToString();
}
public void ExamineStudentsMembers(IStudent anotherStudent)
{
Console.WriteLine(anotherStudent._studentsPrivateMember);
}
}
This will no longer compile due to ExamineStudentsMembers trying to access a private field.
If you are writing the class, you have complete control over it, so if you don't want one object to be able to modify another, don't write in that functionality.
Classes will often use private variables in other instances to implement efficient comparison and copy functions.
Private just means that the member (field/method/etc.) can be accessed only from the within the code of the parent type. From CSharpOnline
Private members of multiple instances are visible and can be invoked. This comes in handy when you are implementing a "copy constructor" or a "clone" method on your type, where the argument is an instance of the same type. If the designers would have made private fields inaccessible, then you may have to create a bunch of getter methods just for clone/copy to get at them. IMHO, I like it better the way it is. Within the same type, Reading another object's state isn't that bad as writing to it though (which could be a DONT-code-convention for you/your team.)
Accessing a sibling's private data may seem wrong when phrased like:
public void ExamineStudentsMembers(Student anotherStudent) {
//this seems very wrong
Console.WriteLine(anotherStudent._studentsPrivateMember);
}
However, it doesn't seem so odd for methods which require this sort of functionality. What methods require accessing a sibling's private data? Comparison methods (in particular equals) and objects in a data structure (say a tree or linked list).
Comparison methods often compare private data directly rather than just the public data.
For a class of nodes that make up a linked list, graph or tree, being able to access a sibling's private data is exactly what is needed. Code in the know (part of the class) can tinker around with the data structure, but code outside of the data structure cannot touch the internals.
It is interesting to note that these two cases are less common in day-to-day programming than when this language feature were first developed. Back in 1990s and early 2000s, in C++ it would have been much more common to build custom data structures and comparison methods. Perhaps it is a good time to reconsider private members.
i like the second point, you can look, but dont touch those private members.
it's funny you should say that, i knew a teacher once and he said he often had a problem deciding what classes it was ok to look at the members and which ones he could actually have a play with.
An object is just a piece of data; the class contains the functionality. A member method is just a nice trick the compiler plays; it's really more like a static method with an implied argument (sort of like extension methods). With that in mind, protecting objects from each other doesn't make any sense; you can only protect classes from each other. So it's natural that it works that way.
No, this is necessary, the method code is not specific to the instance, it is only specific to the type of the object. (virtual methods) or the declared type of the variable (for non-virtual methods). The non-static fields, on the other hand, are instance specific... That's where you have instance-level isolation.
The only difference between a static method and a non-static method is that the static method is not allowed to access other instance based (non-static) methods or fields. Any method that CAN be made static without modification will not be affected in any way by making it static, except to force compiler to throw errors anywhere it was called using instance-based syntax.
If you intend to examine a given student's information then I would change the method to be static:
public static void ExamineStudentsMembers(Student student)
{
Console.WriteLine(student._studentsPrivateMember);
}
You would then use Student.ExamineStudentsMembers(s1). Using s1.ExamineStudentsMembers(s2) would be invalid.
If this isn't the intended purpose I would rewrite the method as:
public void ExamineStudentsMembers()
{
Console.WriteLine(_studentsPrivateMember);
}
The above would then be used by writing s1.ExamineStudentsMembers()
Private members are to hide implementation details from clients. The clients should only see the interface (public methods / fields / properties).
The purpose is not to protect the programmer from himself.
This is also NOT a security feature because you can always access private fields via reflection.
It's really to separate interface & implementation (black box design), and clients programming against a contract (all public fields).
For example if you have a public get property, it could access some private field directly, or it could calculate the value from some other fields.
The purpose is, the client only knows the contract (the public property) and the implementation can be changed without affecting the client
Object scope does not ever imply security - ever! It is role of the OS to provide runtime security. It is a bug to design a system that relies on language specific object scope to limit runtime object instance data access. If this were not the case, then all non OO languages are, by definition, not secure.
I have GUI that allows an user to create and modify a point object. I need to store a list of these points to insert at a specific drawing.
Here's how I came up with it:
In the form code, I opened a private property List<Points> and I manipulate it directly inside form code. Is this the correct way to handle?
Something like:
public partial class TesteInterface_AdicionarVertice : Form {
public List<VerticeDNPM> listaVertices;
public TesteInterface_AdicionarVertice()
{
InitializeComponent();
listaVertices = new List<VerticeDNPM>();
}
}
So, what do you think about this design? Is there a better way to do it?
Thanks for all thoughs.
I will make the list read-only. thanks for that idea.
The real thing here is this: I have a button which creates points, and another that creates polygons from points.
I need to have a way to get the List of points at the time the user chooses to create that certain polygon. That is basically what i am asking :P
I though to use a class property (in this case List) to store temp points, until the user creates the polygon. Is this a valid approach?
Sorry for that. The correct code is:
public partial class TesteInterface_AdicionarVertice : Form
{
public List<VerticeDNPM> listaVertices;
public TesteInterface_AdicionarVertice()
{
InitializeComponent();
listaVertices = new List<VerticeDNPM>();
}
}
Assuming that you include the appropriate namespace inclusions and class definitions, then what you have posted is valid and does not clearly violate any best practices (unless you count naming conventions, in which case VerticeDNPM should be VerticeDnpm according to Microsoft's naming guidelines). However, in order critique your approach from a design standpoint, you'd really need to provide more information.
Thanks for all thoughs.
I will make the list read-only. thanks for that idea.
The real thing here is this:
I have a button which creates points, and another that creates polygons from points.
I need to have a way to get the List of points at the time the user chooses to create that certain polygon. That is basically what i am asking :P
I though to use a class property (in this case List) to store temp points, until the user creates the polygon. Is this a valid approach?
I'm not really sure what you are asking. Aside from moving your non-UI code out of the UI, I would change the list creation to a readonly field like so:
public partial class TesteInterface_AdicionarVertice : Form {
private readonly List<VerticeDNPM> listaVertices = new List<VerticeDNPM>();
public List<VerticeDNPM> Vertices {get; set;};
public TesteInterface_AdicionarVertice()
{
InitializeComponent();
}
}
I agree that making your list public is a bad idea as then a consumer of the class can modify the actual list object itself, which is not what you want. Instead you want to expose it as a read-only property thereby allowing consumers to access the list contents.
public partial class TestInterface_ADicionaryVertice : Form
{
private List<VerticeDNPM> listVertices = new List<VerticeDNPM>();
public List<VerticeDNPM> { get { return listVertices; } }
public TestInterface_ADiciontaryVertice()
{
InitializeComponent();
...manipulate list of points here...
}
}
In this way you are modifying a private list of points in your code while still allowing a consumer (presumably something that receives the form as a parameter?) to access the list of points and read through it.
Two additional thoughts:
1) If the only consumer is deriving from this form instead of operating on it (receiving it as a parameter somewhere) then consider making the list protected instead.
2) If you do not want the list to be modified by any consumer (i.e. the list of points can't change once you're done manipulating them) then consider exposing an enumerator for the list instead of the list itself. This way someone can enumerate the points but can't change them.
Example:
public IEnumerator GetPoints { get { return listVertices.GetEnumerator(); } }
If you give a user access to a read-only property and return the original list, then the a consumer could still modify that list. The List is still a reference type, so the property is returning a pointer to the list. A true read-only property will create a copy of the list inside the 'get' and return that instead.
I wouldn't make your list public. Then you never know who is modifying it. Make your list private, then expose it as read only.
You can read more about it here. You can also run your code through FxCop. I'm sure it would pick this up.
I was working in the Microsoft.Ink dll recently using C# and was debugging a problem (which is not related to this) I noticed, that when I was debugging it, ink objects had a strokes object, which had an ink object, which had.... etc.
This confused me, as I was under the assumption you could not do this (I come from a C++ Background)
But I ignored it, solved the problem, and moved on. Today, I run into a similar problem, as I look at a class which had a private member which was the same class as itself.
public sealed class Factory
{
private static Factory instance = new Factory();
}
How is that even possible? I can now call instance.instance.instance.instance...etc. This, as you can imagine, hurts my mortal brain, and I'm sure it can't be good on the computer either. How does the compiler deal with this? And Just how deep does the rabbit hole go?
Because it's static and therefore there is only one copy of the variable instance within the AppDomain.
What you're thinking of is this:
public class Foo
{
private Foo lol = new Foo();
}
Notice, everything here is instance, not static.
As the commenters noted (long ago), this is valid syntactically, but would result in a StackOverflowException being thrown, as the assignment requires construction, and construction creates a new assignment. One triggers the other in a cycle that ends when the call stack reaches its maximum length.
In OP's example, assignment requires construction, but the assignment is triggered by the static constructor, not the instance constructor. The static constructor only executes once within an AppDomain, in order to initialize the class' Type. It isn't triggered by instance construction, and so (in OP's example) won't result in a stack overflow.
it's not necessarily recursive by nature. think of a linked list. or a tree.
class Directory
{
string name;
Directory parentDirectory;
}
It's just allows objects of that class to have an internal reference to another object of that class.
This is a software pattern known as "Singleton".
Some people frown upon the use of the pattern for more reasons than just stated in the question but for better or for worse it is a common pattern in the .NET Framework. You will find Singleton Properties (or fields) on classes that are meant to be instantiated only once. Think of a static Instance property as a global hook upon which to hang an object.
Since this is a class, and not a struct, when you declare a field that is the class, you are only defining a reference to a class. This allows you to keep having references, provided you assign them.
In your case, you're reference allocates a new class, but it is static, so it's only going to do it one time, no matter how many classes you create. The instance constructor runs the first time Factory is used, and will call a single non-static constructor. Doing instance.instance.instance is not allowed, since instance is static. You cannot access a static variable from a member - you need to do Factory.instance.
However, you ~could~ make instance non-static, and have it be a reference to some other "Factory" class, or even a reference to this. In that case, you could chain instance.instance.instance - but it will just follow the references as long as you've set them. Everything works, no problems.
There will only ever be one instance of 'instance' because it is static. The only way you should be able to access it is by calling Factory.instance.
string text = Factory.instance.ToString(); // legal
string text2 = Factory.instance.instance.ToString(); // compiler error
I think you should ask the other way around: Why shouldn't this be possible? Factory is just a type like any type which gets resolved by the compiler.
As most of the answers here point out that this is working only because Factory is a static field, I have added the following sample. Please note that this is a very primitive sample of a chained list (you probably wouldn't implement it that way for various reasons, but I didn't come up with a better example yet). In this example, ChainedListItem is a container for an element of a single-linked list, which contains a field of the very same type to point to the next item in the list. The list has an (empty) head element and the last element is marked by having an empty _nextItem field:
public class ChainedListItem<T>
{
private ChainedListItem<T> _nextItem;
T _content;
public ChainedListItem<T> NextItem
{
get { return _nextItem; }
set { _nextItem = value; }
}
public T Content
{
get { return _content; }
set { _content = value; }
}
public ChainedListItem<T> Add(T content)
{
_nextItem = new ChainedListItem<T>();
_nextItem.Content = content;
return _nextItem;
}
public void Dump()
{
ChainedListItem<T> current = this;
while ((current = current.NextItem) != null)
{
Console.WriteLine(current._content);
}
}
}
class Program
{
static void Main(string[] args)
{
ChainedListItem<int> chainedList = new ChainedListItem<int>();
chainedList.Add(1).Add(2).Add(3);
chainedList.Dump();
}
}
The "rabbit hole" goes as deep as your stack space allows you to make another call to the constructor of the type. If you try to go deeper than that, you will get a stackoverflow exception as with any other recursion.
By the way, the code that you wrote in your answer is showing a very basic implementation of a Singleton which is actually based on having a (private) static member of the same type as the surrounding type.
And, last but not least, such constructs are also perfectly fine in C++.
It is a singleton. Meaning there is really only one instance of the class.
Is that the entire class? Typically in C# you will see a singleton like
public class SomeClass
{
static readonly SomeClass instance = new SomeClass();
public static SomeClass Instance
{
get { return instance; }
}
static SomeClass()
{
}
SomeClass()
{
}
}
I'm not sure how you would even access the instance since it is private. The only thing this would be useful for is a Singleton implementation, but if that is the case you are mission the public property exposing the instance.
This is done all the time is most OO languages. instance is a static member of Factory. There is nothing unusual about this code. It is standard Factory pattern. Do you also have a problem with code like this?
x = x + 1;