Useclasses without making new instances - c#

I want to take a string in my mainpage and put it inside my class so I can get it in the next window. My Class is simple and looks like this:
name: Spreadsheet
private string itemType;
public string ItemType
{
get { return itemType; }
set { itemType = value; }
}
I can change it just fine if I make a new instance, but that will remove everything inside it - I don't want that. I Call the class using this line:
private Spreadsheet ss = new Spreadsheet();
When I call this method I make a new instance new Spreadsheet() which incorrectly puts all the strings into null. How can I avoid this?

Like Tyler Day said
I think you might be looking for the static keyword. – Tyler Day
That fixed my problems
making the private string itemType into private static string itemType was what I missed out :)
To explain why is that static fields are class-level variables that are per-type rather than per-instance

Related

Why are my values not being kept between instances of a type?

I have the class:
public class pro {
private string url = string.Empty;
public string GetURL() { return url; }
public void SetURL(string value) { url = value; }
}
In this line I'm getting value:
string url = li1.Value;
pro itm = new pro(); // I have create Proprtie so I'm calling that
itm.SetURL(url); // here I'm setting value
Then later:
pro itm = new pro(); //properties object I have created
string url = itm.GetURL(); // I'm not getting value which I have set in first
class.
I have create Proprties also; what am I doing wrong?
May be I understood your problem :
The thing is that in second you create a new instance of pro class. If you want to acess the string value set in first class, you should use that first pro object.
If it's not your problem, please clarify.
Every class instance (i.e. every new pro()) has different instance values; it is perfectly expected that if you have 2 different instances, then they will not share a URL, for example. If you want to share this, you should make the same pro instance available to both places, by passing the pro around.
Incidentally, GetURL() / SetURL() is not idiomatic C# - it would be more common to have a property, i.e.
public string Url {get;set;}
which you would then access as:
YourType item = new YourType();
item.Url = "http://foo.com/bar/";
// ...
string url = item.Url;
From the comments, it sounds like you are talking about static data; I should emphasise that using static for this is not usually a good idea, and can lead to lots of problems with testing, multi-tenancy, threading, etc; but: the following works without any instances:
public class Properties {
public static string Url {get;set;}
}
...
Properties.Url = "http://foo.com/bar/";
...
string url = Properties.Url;
note: no instances at all.
However, it is almost always preferable to simply keep an instance available, and use instance properties against that common instance.
If you need to have some class like application properties you can use static class.
public static class pro
{
public static string Url {get; set;}
}
and use it like pro.Url = "aa";

How can I avoid ref parameters?

I have a method that has 2 ref parameters:
public void ReplaceSomething(ref int code, ref string name)
{
...
}
I want to avoid this, as it is not a good design (and scales poorly). What are my options?
I've though about using an anonymous object, but that doesn't seem like a good idea, either.
Object something = new { code = 1, name = "test" };
ReplaceSomething(something);
Are the code and the name closely linked together? If so, consider creating a type to put the two of them together. Then you can return a value of that type.
Alternatively, you might consider returning a Tuple<int, string>.
(In both cases you can accept an input parameter of the same type, of course. As you haven't shown any of your code, it's not really clear whether you use the existing values of the parameters, or whether they could basically be out parameters.)
Why don't you want to use ref arguments? That seems like a perfectly good way to change some caller values.
The other approach would be to implement a return value. Maybe you need to better explain what the problem is?
If these values are tightly coupled and "belong together" you could define a custom class that holds your properties and either return a new instance (assuming its immutable) of that or update its properties:
class Code
{
public int Value {get;set;}
public string Name {get;set;}
}
public Code UpdateCode(Code code)
{
...
}
If you need to return these values, you can either use a tuple
public Tuple<int, string> ReplaceSomething(int code, string name)
{
...
}
Or create your own class-wrapper that holds the values as properties
public Foo ReplaceSomething(int code, string name)
{
var foo = new Foo(){...};
return foo;
}
class Foo
{
public int IntValue{get;set;}
public string StringValue{get;set;}
}
Why would you change it? ref parameters make sense at times, and if this is one of those times - use them. You could introduce a new class that contains that pair of values, which only makes sense if those values come together often.
I say, keep it.
Based on your question, I could be way off. What do you mean by replacing ref? Are you looking to overload?
public void ReplaceSomething(int code, string name)
{
// ...
}
public void ReplaceSomething()
{
return ReplaceSomething(1, "test");
}
Edit:
ok, so you need to return the code and the name what are the calculations that need to be made? Jon Skeet's answer about a tuple could be right, or you might need a POCO that contains the code the name and the replaced
public void ReplaceSomething(int code, string name)
{
var replaced = new Replaced();
replaced.code = code;
replaced.name = name;
var r;
// do some replacement calculations
replaced.replaced = r;
return replaced;
}
public class Replaced {
public string name {get; set;}
public int code {get; set;}
public string replaced {get; set;}
}

Need work-around for overriding RoutedUICommand.Text property

I have a static Command class like this (but with many more commands):
class GuiCommands
{
static GuiCommands()
{
addInterface = new RoutedUICommand(DictTable.getInst().getText("gui.addInterface"), "addInterface", typeof(GuiCommands));
removeInterface = new RoutedUICommand(DictTable.getInst().getText("gui.removeInterface"), "removeInterface", typeof(GuiCommands));
}
public static RoutedUICommand addInterface { get; private set; }
public static RoutedUICommand removeInterface { get; private set; }
}
It should use my dictionary to get the texts in the right language, which doesn't work, because my dictionary isn't initialized when the static constructor is executed.
My first attempt was to create a new command-class which derives from RoutedUICommand, override the Text property and call the dict in the get method. But the Text property isn't virtual and neither is the GetText()-Method it calls.
The only thing i can think of is provide a static initialize method in this class that translates all the dict-keys. But this is not very clean IMHO because i have to name every command once again like this
addInterface.Text = DictTable.getInst().getText(addInterface.Text);
and if i forget to name one, there won't be an error, just no translation.
I don't even like that i have to name the command twice in this class and once again in the XAML commandbindings.
Do you have any ideas how this can be solved more elegantly?
I like RoutedUICommands much, but like this they're useless to me. Why couldn't Microsoft add the little word 'virtual' a little more often?? (or make it default like JAVA does?!)
I found an acceptable way by translating all commands automatically using reflection.
This way i at least don't have to add all the commands to another method.
I call the translate-method right after i initialized my dictionary.
public static void translate()
{
// get all public static props
var properties = typeof(GuiCommands).GetProperties(BindingFlags.Public | BindingFlags.Static);
// get their uicommands
var routedUICommands = properties.Select(prop => prop.GetValue(null, null)).OfType<RoutedUICommand>(); // instance = null for static (non-instance) props
foreach (RoutedUICommand ruic in routedUICommands)
ruic.Text = DictTable.getInst().getText(ruic.Text);
}

What is a good way to handle enums that need to be strings

I'm pretty sure an enum isn't what I want. What I want is a list of named items
CustomerLookup = "005",
CustomerUpdate = "1010"
The "005" and "1010" aren't my values, they are the values I need to send to a 3rd party that I have no control over. There are close to 500 of them. I just want my code to look nice.
Instead of
SendRequest("005");
I'd rather see
SendRequest(RequestType.CustomerLookup);
Anyone have any self-documenting ideas without getting all crazy in the code?
Anything wrong with:
public static class RequestType
{
public static readonly string CustomerLookup = "005";
// etc
}
or
public static class RequestType
{
public const string CustomerLookup = "005";
// etc
}
? Or if you want more type safety:
public sealed class RequestType
{
public static readonly RequestType CustomerLookup = new RequestType("005");
// etc
public string Code { get; private set; }
private RequestType(string code)
{
this.Code = code;
}
}
That will basically give you a fixed set of values (the constructor is private, so outside code can't create different instances) and you can use the Code property to get at the related string value.
How about using some kind of associative array?
The way you are already doing it seems right to me.
You are clearly defining the requesttype values in your code without ambiguity and when you come to use them you have intellisense on your side.
I think the real issue is how to get the 500 values into your code without any tyypos!

Is it OK to use a public variable in C# if it is readonly?

Is there some internal difference between the C# syntactic sugar way of making properties:
public string FirstName { get; set; }
and just making public variables like this:
public string LastName;
I assume the first way is preferred and the second to be avoided. However, I often see this type of readonly property being used which is a form of the second type above:
public readonly string InternalCode;
Is this a best-practice way to create readonly property?
using System;
namespace TestProps
{
class Program
{
static void Main(string[] args)
{
Customer customer = new Customer();
customer.FirstName = "Jim";
customer.LastName = "Smith";
customer.Show();
}
}
class Customer
{
public string FirstName { get; set; } //prefered
public string LastName; //avoid
public readonly string InternalCode; //???
public Customer()
{
InternalCode = "234729834723984";
}
public void Show()
{
Console.WriteLine("{0}, {1} ({2})", LastName, FirstName, InternalCode);
Console.ReadLine();
}
}
}
Since he didn't answer (yet) and no one else referenced this yet: There is a great article on this topic by Jon Skeet amending his book C# in depth (give credits to Jon):
Why Properties Matter
Using a property provides an interface which is more resistant to change in the future. Let's say some time in the future, a decision is made to add a prefix to the internal code.
Using a public readonly variable exposes your internal structure and you will have a hard time adding the prefix to every line you used the internal variable of the class.
Using a Property, you can just write the following
public string InternalCode {
get { return _prefix + _internalCode; }
}
and you're done!
In my opinion, it's ok to expose public fields (especially if they're readonly or const). Having said that, I'd say that in the example you're presenting, I'd probably go with properties since they'll give you 2 advantages (over fields): 1) better encapsulation and may let you adapt your code in the future and 2) if you're doing data binding, then you do need the properties.
Yes. it is OK to have a public readonly variables (it is just that they can be initialized at the time of definition or constructor).
e.g. Decimal.MaxValue
Having public readonly property is good, if the backing value changes (other than what it was initialized with).
e.g. Environment.TickCount
I thought that Environment.NewLine will be a public readonly variable. Well, it is a public property (get only) and the reason could be to maintain compatibility across different platform.
Short answer: public const is ok, public readonly not necessarily, public get without set not neccessarily.
Objects that cannot be changed without being assigned can be ok. Reference types are dangerous as you can still change their values, even if you cannot change the reference itself.
The problem with the readonly keyword is that it does not mean what you'd understand as logically readonly/immutable. It means more like "can only be assigned in constructor". References cannot be changed, but its values can. There is no "real" readonly keyword provided by c#, unfortunately. See also https://blogs.msdn.microsoft.com/ericlippert/2007/11/13/immutability-in-c-part-one-kinds-of-immutability/
Properties cannot have the readonly keyword (https://titombo.wordpress.com/2012/11/11/using-the-c-modifiers/).
As others noted, you can use a property and only define get and no set, though you cannot set that property in the constructor. Using a private set, you can set the property from annywhere in the class, not only in the constructor. The readonly field would be a little more restrictive.

Categories

Resources