I'm a newbie to C# so forgive this question but I'm confused: Why do I need an instance of class Program to access method Sandbox which is public and in the same class?
namespace GoogleTest
{
class Program
{
static void Main(string[] args)
{
Program p = new Program();
p.Sandbox();
}
public void Sandbox()
{
...
}
}
}
public void Sandbox()
{
...
}
is the important part: This method is not marked static, so it is not callable on the class, but on instances of the class. If you want to be able to call it directly, you need
public static void Sandbox()
{
...
}
and can't use this.
Because you're trying to access it from within a static method, but Sandbox is an instance method.
If you make Sandbox static, this won't be required:
static void Main(string[] args)
{
Sandbox();
}
public static void Sandbox()
{
...
}
Note that it also doesn't have to be public - public allows it to be used by other classes and within other assemblies, but within Program, that's not required.
Static methods exist at the Class level, you can consider them Global functions. Any non static methods are instance level and just as the name implies you can only execute instance methods on an instance. So by instantiating the class you have created an instance and now can call any public method. In your example you could also call any private methods or constructors because you are creating the instance from with the class you are creating.
Related
I want to call a static void function from another class, but it's said
The name [funcion name here] does not exist in the current context
Each class is in the same project, Framework 4.5.2
Its a public static void Function, in a public static class, don't see why it's not working.
The class where a function located, I want to call:
namespace Client.Modules
{
public static class Login
{
public static void Run()
{
// do something
}
}
}
The class where I want to call:
using Client.Modules;
namespace Client
{
public class Main
{
Login.Run(); // here
}
}
public class Main
{
Login.Run(); // here
}
That’s invalid: You can’t generally execute code outside methods. The only things that can go directly into classes are declarations. Put Login.Run() inside a method.
I cannot seem to figure out the following:
For a school project i need to run a simple program. The program has to be a console application. But i need to have a few classes, from which i need to refference a variable from the main class.
class Program
{
public K[] ksmall = new K[number];
static void Main(string[] args)
{
//do somethings with ksmall
}
}
class K
{
//something
}
class A
{
public void SomethingElse()
{
//do something with ksmall
}
}
I hope my example makes sense. So anyway, how can i acces the ksmall from class A. When i start creating instances of Program, i get null references. is there any possible way to make both classes acces the same ksmall?
As ksmall is a non-static variable, so a static function (Main in your case) can't access it.
So, you can declare ksmall as static:
public static K[] ksmall = new K[number];
So now you can access ksmall from Main function as well as from other class functions as "Program.ksmall".
You should re-think about the architecture of your project, for example some OOP principles will give you more tools. I would recommend having your classes designed that you can either pass the object you want to share by a parameter in a constructor or in your methods. Another thing be careful with the encapsulation of your classes (private is by default, public anyone, protected inside the same namespace, private).
I hope this help you to get more understanding of the problem no the symptom.
Two ways to go about it.
First is that you could make a third, static class to hold ksmall (and any other variables you want to access from anywhere in the future)
class Program
{
public K[] ksmall = new K[number];
static void Main(string[] args)
{
VariableHolder.ksmall = new K[0];
}
}
public class K
{
//something
}
public class A
{
public void SomethingElse()
{
//do something with ksmall
}
}
public static class VariableHolder
{
public static K[] ksmall = new K[number];
}
The other option is the pass ksmall into the method within the class as a parameter.
class Program
{
public K[] ksmall = new K[number];
static void Main(string[] args)
{
A classAInstance = new A();
classAInstance.SomethingElse(ksmall);
}
}
class K
{
//something
}
class A
{
public void SomethingElse(K[] kSmall)
{
kSmall[1] = new K();
//do something with ksmall
}
}
You need to make the class K public.
public class K
{
//something
}
I have a static class with a static constructor. I need to pass a parameter somehow to this static class but I'm not sure how the best way is.
What would you recommend?
public static class MyClass {
static MyClass() {
DoStuff("HardCodedParameter")
}
}
Don't use a static constructor, but a static initialization method:
public class A
{
private static string ParamA { get; set; }
public static void Init(string paramA)
{
ParamA = paramA;
}
}
In C#, static constructors are parameterless, and there're few approaches to overcome this limitation. One is what I've suggested you above.
As per MSDN, A static constructor is called automatically to initialize the class before the first instance is created. Therefore you can't send any parameters.
CLR must call a static constructor, how will it know which parameters to pass it?
So don't use a static constructor.
Here's the work around for your requirement.
public class StaticClass
{
private int bar;
private static StaticClass _foo;
private StaticClass() {}
static StaticClass Create(int initialBar)
{
_foo = new StaticClass();
_foo.bar = initialBar;
return _foo;
}
}
Static constructors have the following properties:
A static constructor does not take access modifiers or have parameters. A static constructor is called automatically to
initialize the class before the first instance is created or any
static members are referenced.
A static constructor cannot be called directly.
The user has no control on when the static constructor is executed in the program.
A typical use of static constructors is when the class is using a log file and the constructor is used to write entries to this file.
Static constructors are also useful when creating wrapper classes for unmanaged code, when the constructor can call the LoadLibrary
method.
If a static constructor throws an exception, the runtime will not invoke it a second time, and the type will remain uninitialized for
the lifetime of the application domain in which your program is
running.
If by "HardCodedParameter" you really mean hard coded, you can use constants.
public static class YoursClass
{
public const string AnotherHardCodedParam = "Foo";
}
public static class MyClass
{
private const string HardCodedParam = "FooBar";
static MyClass()
{
DoStuff(MyClass.HardCodedParam);
DoStuff(YoursClass.AnotherHardCodedParam);
}
}
Also, you can use static readonly properties.
Constructors on non-static class have have the benefit to ensure they're properly initialized before they're actually being used.
Since static classes don't have this benefit, you have to make ensure that yourself.
Use a static constructor with an obvious name, then in the relevant portion of your static procedures check to make sure the initialization has been performed.
The example below assumes your want to "initialize" your static class with a Form object.
public static class MyClass
{
private static Form FormMain { get; set; }
public static void Init(Form initForm)
{
FormMain = initForm;
}
private static bool InitCheck()
{
return FormMain != null ? true: false;
}
public static void DoStuff()
{
if (InitCheck())
{
// Do your things
}
else
{
throw new Exception("Object reference not set to an instance of an object");
}
}
}
In Obj-c there is the static Initialize method which is called the first time that class is used, be it statically or by an instance. Anything like that in C#?
You can write a static constructor with the same syntax as a normal constructor, except with the static modifier (and no access modifiers):
public class Foo {
static Foo() {
// Code here
}
}
Usually you don't need to do this, however - static constructors are there for initialization, which is normally fine to do just in static field initializers:
public class Foo {
private static readonly SomeType SomeField = ...;
}
If you're using a static constructor to do more than initialize static fields, that's usually a design smell - but not always.
Note that the presence of a static constructor subtly affects the timing of type initialization, requiring it to be executed just prior to the first use - either when the first static member access, or before the first instance is created, whichever happens first.
There is a static constructor. As per msdn:
A static constructor is used to initialize any static data, or to perform a particular action that needs to be performed once only. It is called automatically before the first instance is created or any static members are referenced.
public class Foo
{
static Foo() {} //static constructor
}
Yes, it is called a constructor.
By MSDN:
public class Taxi
{
public bool isInitialized;
//This is the normal constructor, which is invoked upon creation.
public Taxi()
{
//All the code in here will be called whenever a new class
//is created.
isInitialized = true;
}
//This is the static constructor, which is invoked before initializing any Taxi class
static Taxi()
{
Console.WriteLine("Invoked static constructor");
}
}
class TestTaxi
{
static void Main()
{
Taxi t = new Taxi(); //Create a new Taxi, therefore call the normal constructor
Console.WriteLine(t.isInitialized);
}
}
//Output:
//Invoked static constructor
//true
Consider this example code:
public class A<T>
{
public static T TheT { get; set; }
}
public class B : A<string>
{
static B() {
TheT = "Test";
}
}
public class Program {
public static void Main(String[] args) {
Console.WriteLine(B.TheT);
}
}
Here B.TheT is null. However, changing the Main method like this:
public static void Main() {
new B();
Console.WriteLine(B.TheT);
}
B.TheT is "Test", as expected. I can understand that this forces the static constructor to run, but why does this not happen for the first case?
I tried reading the spec, and this caught my attention (§10.12):
[...] The execution of a static constructor is triggered by the first of the
following events to occur within an application domain:
• [...]
• Any of the static members of the class type are referenced.
My interpretation of this is that since TheT is not a member of B, the static constructor of B is not forced to be run. Is this correct?
If that is correct, how would I best let B specify how to initialize TheT?
A.TheT is "Test", as expected. I can understand that this forces the static constructor to run, but why does this not happen for the first case?
Basically, you haven't really referenced B. If you look in the IL, I think you'll find that your code was actually equivalent to:
public static void Main(String[] args) {
Console.WriteLine(A<string>.TheT);
}
The compiler worked out that that's really the member you meant, even though you wrote B.TheT.
If that is correct, how would I best let A specify how to initialize TheT?
I would try to avoid doing this to start with, to be honest... but you could always just add a static method to B:
public static void Initialize() {
// Type initializer will be executed now.
}
Static constructor is called before the first access or at the latest when the first access is made. I.e you know it has been called when first access is made but not how long before. However, if no access is made it won't be called. So you cannot control when only if it s called.
As per MSDN reference
A static constructor is used to initialize any static data, or to perform a particular action that needs performed once only. It is called automatically before the first instance is created or any static members are referenced.
In second case called static contructor and it will call the actual types' static contructor, and not that one of derived one. So in your case it calls the static ctor of the A<T> =>A<string> and not of A.
To prove this behaviour just do the following:
public class Base {
static Base() {
"Base static".Dump();
}
}
public class Derived : Base {
static Derived() {
"Derived static".Dump();
}
public static string temp = "Hello";
}
and call
Derived.temp.Dump();
You will get:
Derived static
Hello
This is what you actually do in your code, you acess derived type A<string> and it's default static ctor is called.