I am using VS 2010 and C# windows forms.
I need the user to enter how many objects he has and how much each weights.
I then need to process each one. I typically use for each datarow in row collection.
Question is i tried cleaning up some of my Very Nasty code (this is my first real project ever btw) I have one main class at ~5000 lines of code and would like to break up specific sets of modules into there own classes. The problem is when the user enters info i have to set up a dataset on the main form (DSObjects) and link a table grid view and a couple of entry boxes with an add button to it so the user can add the data they need. The issue I am having is when I run the code and break up the class into sub classes the dataset is wiped out on each new class.
Do not create a new instance of the data set in every class, but pass one instance around, like:
public class AnotherClass
{
private DataSet m_dataSet;
public AnotherClass(DataSet ds)
{
m_dataSet = ds;
}
}
When creating a new instance of AnotherClass use:
AnotherClass ac = new AnotherClass(m_dataSet);
where m_dataSet is again a member variable that references the data set - either passed to the calling class in the constructor, or (in case of the main class) being created somewhere in the code.
Only create the data set once, for example in the main class.
Another approach could be to use a singleton class that holds an instance to the data set. The singleton could then be accessed from lots of different objects.
A non-threadsafe sample would be:
public class DataHolder
{
private DataSet m_dataSet;
private static DataHolder m_instance;
private DataHolder()
{
m_dataSet = ... // Fill/Create it here
}
public static DataHolder Instance
{
get
{
if (m_instance = null)
m_instance = new DataHolder();
return m_instance;
}
}
public DataSet Data
{
get { return m_dataSet; }
}
}
Then, access it using DataHolder.Instance.Data;
You could try passing the dataset into the constructor of each class
var something = new Something(dataset)
Keep in mind that a DataSet is actually a small (but complete) database in memory. While most applications just use it to transfer data from a database server to objects in the application, it has all the parts of a full database: multiple tables, which can be joined be relationships, which can have queries run against them.
With that in mind, just as you wouldn't have separate databases for each class, but instead have one used globally for the whole application, it is similarly quite reasonable to have one DataSet shared by all objects in the application.
Related
I'm unsure how to word this question but I have a question regarding how asp.net and C# handle "instances" or "copies" of the source that runs and if there can be any sort of "cross pollination" between them when used by different users.
To summarise the question, can person A who is using the website at a particular time, get access to things that person B is doing if they are also on the website at the same time (this is what I want to avoid and confirm).
I understand how OOP works and this question is adding a layer on top of that to understand how isolated the code gets as will be described below.
For example, say there are 10 users who have signed up for a system with individual authentication (as created by VS).
And you have source code that you've written which performs various functions.
When person A uses the website and performs various operations, do they have their own "copy" of the source that's running for them?
If person B decides to use the website at the same time, do they also have their own "copy" of the source or are they using the same source that's also being used for person A?
As I understand it, every time you have a class and you instantiate it using a constructor, you have a new object of that item which is used and then destroyed later on when not needed.
Taking this thought one step above, does a user who's using the system have their own copy of the whole isolated source?
For example, there are static classes where there is only ever going to be 1 instance of it all the time. Does person A share the same static class as person B or do they each have their own static class?
Say for example, I have a class, which has global properties instead of method properties.
public partial class HelperMethods
{
private static string Item1 = "StaticString1";
private const string Item2 = "constString2";
private const string Item3 = "constString3";
public BlockingCollection<Task> Collection1 = new BlockingCollection<Task>();
public BlockingCollection<Task> Collection2 = new BlockingCollection<Task>();
public BlockingCollection<Task> Collection3 = new BlockingCollection<Task>();
public BlockingCollection<Task> Collection4 = new BlockingCollection<Task>();
public ApplicationUser CurrentUser { get; set; }
public HelperMethods(int id) {
using (var database = new DatabaseEntities()) {
CurrentUser = //database call here with ID.
}
}
}
Does user A and user B have their own separate copy of all these items (for example Collection1) or are these items shared between each other?
If user A adds items to Collection1, and at the same time user B adds items to Collection1, would they be adding the items to the same collection or would they be completely separate from each other?
So to simplify and summarise briefly what I am trying to understand, when user A and user B both log onto the website, do they each get a copy of "HelperMethods" (let's say HelperMethods is the whole program for simplicity) and is isolated from each other or does C# do something else where there's actually ever only one copy of HelperMethods and every user that uses the system just get the constructor method and share everything else that's in global parameters?
An image example would be as follows:
Scenario 1:
Person A
(Has copy of class HelperMethods and all items in it.)
Person B
(Has copy of class HelperMethods and all items in it.)
Scenario 2:
(HelperMethods - exposes all global parameters)
Person A (has copy of the HelperMethod constructor only.)
Person B (has copy of the HelperMethod constructor only.)
Thanks
The static members of the HelperMethods class will be shared across all users. They will not be separate for each request/user.
A static member is owned by the ASP.NET worker process, it is common for all users. The instance variables of course will be separate for each user.
I am currently learning basics of c# window forms in visual studios and wondered how I use common cs files. I want to transfer variables from one file to another and I believe an easy way to do this is with a common cs file that just stores the variable and then i just reference it from each of the forms. So my questions are. How do i lay out the code for this common cs file ? if i reference the value in one form and then reference it in the next will it display the value recorded in the previous form or restart from 0. Thanks for any help!
A couple of things. I would remove the basic tag from this post, as that is a different language altogether and might elicit some weird responses.
Your question seems to confuse the cs file with objects and references. So first up, there is nothing magical about a .cs file. It is just a file where c# code is. Often there is a 1-class-per-file convention, but this is just a developer aid, not a requirement. Your data itself will be in an object instance, and that object instance is defined by a class (that happens to be in a cs file).
A simple class definition might look like this
public class Person
{
public int Id
{
get;
set;
}
public string Name
{
get;
set;
}
}
Then your first form can create an instance of a person like this:
Person bob = new Person();
bob.Id = 1;
bob.Name = "Bob Dylan";
(or perhaps you would be assigning values from a control)
You then need to pass your person object instance to your other form. There are several ways that can be done and without understanding your problem domain, I cannot make judgement on which would be most appropriate. But if your second form had a public Person property, you could do something as simple as
Form2 secondForm = new Form2();
secondForm.Person = bob;
secondForm.Show();
or passing via constructor (if that is how it is defined)
Form2 secondform = new Form2(bob);
secondForm.Show();
Now your secondForm instance can access that bob object created above, either via the Person property, or within the constructor depending on how you wrote it.
Whilst this could also be done using static classes or even singletons, I think that until you are completely clear about regular classes, the use of these has the potential to lead you into various "code smells".
I have a question about how to setup components in a winforms application so they can interact with each other. But I want to use the visual designer to set this up.
What I have is a component called myDataBase and a component called myDataTable.
Now the component myDataTable has a property of type myDataBase.
So in code I can do
myDataBase db = new myDataBase();
myDataTable dt = new myDataTable();
dt.DataBase = db;
The property DataBase in component myDataTable is public, so I can also use the visual designer to assign the DataBase property.
Now for my problem.
I have many many forms that have one or more components of myDataTable on it.
I only want one instance for myDataBase.
What I do now is I create a component myDataBase dbMain = new myDataBase() on the mainform.
On every form I have to set the property for all myDataTable components to this dbMain.
I have to do this in code because the visual designer cannot see the dbMain component on the mainform.
So the question is, can I create one instance of component myDataBase that is visible to the visual designer on all forms, so I can use the visual designer to set the property of myDataTable components ?
For those that now Delphi, I want something like the DataModule in Delphi.
You can't without some code.
The easiest thing you can do, as far as I am concerned, it to create a base form, deriving from Form, and in that form, you make a property pointing to a singleton instance of your database object. You can bind to that property, and still keep it as simple as possible.
You just need to make your form derive from this one:
public class DatasourceForm : Form
{
public myDataBase DataBase
{
get
{
return myDataBaseFactory.Current;
}
}
}
And the factory in charge of creating the singleton database instance:
public class myDataBaseFactory
{
private static readonly Lazy<myDataBase> lazy =
new Lazy<myDataBase>(() => new myDataBase());
public static myDataBase Current { get { return lazy.Value; } }
}
(Singleton implementation from here)
I need simple way to persist and edit a set of string pairs in my application. I believe that DataGridView with two culmns can help me with viewing and editing, and I was hoping to use application settings instead of database to store data (maybe a DataSet as setting type). I just can't put all that together. Is there a way?
Here's how I did it. Class MyMap holds value pairs. They must be properties, because DatGridView doesn't work with fields. MyMapCollection holds the collection of MyMaps, as BindingList (allows adding rows in DataGridView). This class is needed to make Visual Studio settings editor happy, couldn't make it work with plain BindingList. So:
public class MyMap {
public String FirstField { get; set; }
public String SecondField { get; set; }
}
public class MyMapCollection : BindingList<MyMap>
{
public MyMapCollection Clone()
{
MyMapCollection result = new MyMapCollection();
foreach (MyMap map in this)
result.Add(new MyMap() {
FirstField = map.FirstField, SecondField = map.SecondField });
return result;
}
}
Function Clone creates a deep copy of the object, so that data is not changed directly on the object in Settings.Default, but when the users says so. In settings editor you would add an item of type MyMapCollection, called say TheValues, and use very simple it in the code:
myDataGridView.DataSource = Settings.Default.TheValues.Clone();
If data should be changed back to settings (when users clicks OK) then change settings accordingly:
Settings.Default.TheValues = (MyMapCollection)myDataGridView.DataSource;
Using a DataTable or DataSet instead of MyMapCollection is also possible, but this solution allows me to use TheValues in the rest of the code, which is even sweeter than DataSet could have been.
If the values that you are trying to edit are plain key value pairs, you can create a class which holds these values as properties and serialize this class object into an XML file. You can deserialize the class and assign the values to the DataGridView.
You could also create a custom configuration and store it separately from App.config / Web.config file. This will be similar to what NHibernate or spring.Net configuration files are stored with a reference to them in the configsections key.
Here is a link how to creat your own custom configuration.
MSDN link
I'm trying to learn this tutorial http://www.devx.com/dotnet/Article/28678/1954 in C#, I have created the datatables but when I want to type
DsActivitiesTasks.Tasks.AddTasksRow("Email")
Intellisense doesn't see Tasks but only TasksRow and TasksDataTable and none have add method.
Did I forget to do something ?
DsActivitiesTasks is the name of the class generated by the designer.
Tasks is an instance property of that class, so you can only access it from an instance of the dataset.
Try creating a new instance of DsActivitiesTasks, like this:
new DsActivitiesTasks().Tasks.AddTasksRow("Email");
Note that this code will throw away the new dataset; you'll need to store it somewhere in a field or property.
For example:
public static readonly DsActivitiesTasks Database = new DsActivitiesTasks();
//In some method:
Database.Tasks.AddTasksRow("Email");
Note that datasets are not thread-safe, so you must not work with it on multiple threads.
Instantiate DsActivitiesTasks.