Getting value pointer and use it from somewhere else - c#

First , I'm a C++ dev and new to C# , Sorry for this simple question.
I'm creating a wrapper for my native library.
I want to pass a value in a class and edit it from some other function in class , like pointers in C++ , I found out it can be done with unsafe mode but I need to do it without unsafe and I'm sure it's possible.
Here's my code :
Main Console
namespace ConsoleApp2
{
class Program
{
[STAThread]
static void Main(string[] args)
{
string DATA_VALUE = "Not Set Yet";
new Data_Picker_Form(DATA_VALUE).ShowDialog();
Console.WriteLine("Value is {0}", DATA_VALUE);
Console.ReadKey();
}
}
}
Form Code
using System;
using System.Windows.Forms;
namespace ConsoleApp2
{
public partial class Data_Picker_Form : Form
{
object data_in_obj;
public Data_Picker_Form(string data_in)
{
InitializeComponent();
data_in_obj = data_in;
}
private void button1_Click(object sender, EventArgs e)
{
string data_in_new = data_in_obj as string;
data_in_new = "OUTPUT_VALUE";
this.Close();
}
}
}
it's not working unfortunately , so I need to pass my string , int and etc. value to a new form , in initializing form creates a instance [like pointer] to original string and it can accessible from other functions ins class like button click.
thanks.

You already have a reference (sort of like a pointer), and that is your problem (well, half of it anyways).
string data_in_new = data_in_obj as string;
Says to create a variable that holds a string reference (as strings are immutable reference types) and copy the reference data_in_obj currently has to it. When you then reassign data_in_new it of course doesn't affect any other variable (just like it wouldn't in C++).
Because strings are immutable, there is no way for that code to affect other things that point to that string (passing by reference aside, but this is about variables/members). You need to store it in a simple struct or class so that everyone is pointing at an object that holds the current string reference, and can be updated.
Same idea with your int, it is actually a value type so any copy will copy the actual value, you can't change a different variable through it. You need a wrapper class so that each user is pointing at the same object.

What about setting up a simple get and set function since you are already Initializing your Form?
In Your Form:
private string data_in_new = "";
public Data_Picker_Form(string DATA_VALUE)
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
Data_in_new = "OUTPUT_VALUE";
Close();
}
public string Data_in_new
{
get
{
return data_in_new;
}
set
{
data_in_new = value;
}
}
And in your Console:
class Program
{
static void Main(string[] args)
{
string DATA_VALUE = "Not Set Yet";
Data_Picker_Form D_P_T = new Data_Picker_Form(DATA_VALUE);
D_P_T.ShowDialog();
DATA_VALUE = D_P_T.Data_in_new;
Console.WriteLine("Value is {0}", DATA_VALUE);
Console.ReadKey();
}
}
This Way you can access you value at any desired point in the project.

Related

'Internal' Variable through function

I am trying to create code for a DLL that will manage, create and return variables to the program using it. I could just not use a DLL but I want my code to be less cluttered and also to save time in "if var == whatever" statements.
Here is my code so far:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace JERK_mgr
{
class Program
{
static void Main(string[] args)
{
// DLL file that makes managing, reading and creating variables easier
// >>J03L<<
// v0.0-initial
newVar("", "");
Console.WriteLine(TESTVAR);
}
internal static void newVar(string name, object value);
{
public const string TESTVAR = "hey it actually worked! :D";
}
}
}
At this moment in time I don't intend for it to do anything but the following:
- Be called from Main
- create a variable that can then be accessed through Main and any other methods.
I am aware that I may be using internal incorrectly here, but it was just an attempt at getting it to work and just used to be public.
What then happens is I get an error at
internal static void >>newvar<<(string name, object value)
saying it must declare a body, but this isn't my main problem, atleast as far as I know.
I then get an error at
internal static void newvar(string name, object value)
>>{<<
I also notice that
internal static void newVar(string name, object value);
{
public const string TESTVAR = "hey it actually worked! :D";
>>}<<
when hovered over or selected, says it matches up to
class Program
{
So I ask, how do I have a function that is not the Main function declare a variable that is accessible throughout any other function, including the Main function?
EDIT1: I think I have found a way to make the variables how I want them, but now I am facing the problem of mismatching curly brackets even though they should match (can be seen at https://imgur.com/a/scBYuaH)
I think the question you are really asking is "how do I write a function that defines global variables?" If that really is your question then the answer is C# (any many other object oriented languages) won't allow it. (unless maybe you use some twisted kind of reflection code.)
remove ; after (string name, object value)
and it's a function you can't declare a public const value in the function try to move to outside.
class Program
{
public string TESTVAR = "hey it actually worked! :D";
internal static void newVar(string name, object value)
{
}
static void Main(string[] args)
{
//....
}
}
how do I have a function that is not the Main function declare a
variable that is accessible throughout any other function, including
the Main function?
While you can't dynamically create variables, you can do something like:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApp29
{
class Program
{
public static dynamic Vars = new System.Dynamic.ExpandoObject();
static void AddorUpdateVar(string name, object value)
{
var vd = (IDictionary<string, object>)Vars;
vd[name] = value;
}
static void Main(string[] args)
{
AddorUpdateVar("Hello", 213);
var a1 = Vars.Hello;
AddorUpdateVar("Hello", "World");
var a2 = Vars.Hello;
Vars.Hello = new int[] { 7, 3 };
var a3 = Vars.Hello;
}
}
}

c# how to use Property

I want to learn more about c#, and I've heard that you should use Private specifier and use get/set to make it public.
I got a small application that take textbox data and writes it to a file. And it encrypts the file.
But I can't graps the concept about getters and setters. Here is my one of my classes and Methods that writes to a file.
class MyClass
{
public static bool WriteToFile(string text)
{
string FileName = "C:\\crypt\\crypt.txt";
try
{
using (System.IO.StreamWriter WriteToFile = new System.IO.StreamWriter(FileName))
{
WriteToFile.Write(text);
WriteToFile.Close();
}
return true;
}
catch
{
return false;
}
}
But instead i want to use a property. How should i do it?
This is how i pass in the textbox-data from my main class.
public void button1_Click(object sender, EventArgs e)
{
MyClass c = new MyClass();
if (MyClass.WriteToFile(textBox1.Text))
MessageBox.Show("success, managed to write to the file");
else
MessageBox.Show("Error, Could not write to file. Please check....");
I've looked at various tutorials such as https://channel9.msdn.com/series/C-Fundamentals-for-Absolute-Beginners/15 and tutorials, but I really stuggling.
WriteToFile is a method.
Methods are methods, and properties are properties.
Methods encapsulate behaviour, while properties encapsulate state.
WriteToFile should not be a property, because it does not encapsulate state. In fact, it attempts to write into the file system.
An example of a property would be:
public class MyClass
{
private bool _canWrite;
/// Checks whether the file can be written into the file system
public bool CanWrite
{
get { return _canWrite; }
}
}
From another class, you would call it like this:
if(myClass.CanWrite)
{
// ...
}
Notice that CanWrite does not define any behaviour, it just defines a getter for the _canWrite field, this ensures that external classes don't get to see too much about your class.
Also notice that I define a getter only, this prevents others from setting your property.
There is not much to change to your design besides one little thing. But first things first:
Could you place that code into a property? Sure. Should you? Not at all. Your method WriteToFile is actually doing sth. and thats what methods are for. Properties on the other hand are used for modifying/storing data.
Thats why property-names sound more like Names while method-names generally sound like Commands:
Example
public class Sample
{
private string someText;
// This Property Stores or modifies SomeText
public string SomeText
{
get { return this.someText; }
set { this.someText = value; }
}
// Method that does sth. (writes sometext to a given File)
public void WriteSomeTextToFile(string File)
{
// ...
}
}
Why properties/modifiers?
it is considered good pratice to encapsulate data within propeties like in the example above. A small improvement could be the use of an AutoProperty like so:
public string SomeText { get; set; }
which basically results in the same structure as the combination of an encapsulated field like in the first example.
Why?: because this makes it easy to switch it out or to add logic to your get/set-operations.
For example, you could add validation:
public string SomeText
{
// ...
set
{
if (value.Length > 100)
throw new Exception("The given text is to long!");
this.someText = value;
}
}
SideNote: Possible improvement to your class
The only improvement I could think of is not to swallow the exception in your write method:
public void WriteToFile()
{
using (var fileWriter= new System.IO.StreamWriter(FileName))
{
fileWriter.Write(_text);
fileWriter.Close();
}
}
This is much cleaner and you would not have to "decision" cascades handling the same issue (your try/catch and if/else) are practically doing the same.
public void button1_Click(object sender, EventArgs e)
{
try
{
var c = new MyClass();
c.WriteToFile(textBox1.Text))
MessageBox.Show("success, managed to write to the file");
}
catch(Exception e)
{
MessageBox.Show("Error, Could not write to file. " + e.Message);
}
}
This way, you do not only have the same behaviour, but you also have more information than just the raw fact that your operation was unsuccessful (false)
Okay so I think for you case you don't need a property, but if we assume you wan't to create some kind of wrapper class that handles all your writing to files you could do something along the lines of
class AwesomeFileWriter
{
private const string FileName = "C:\\crypt\\crypt.txt";
private readonly string _text;
public AwesomeFileWriter(string text)
{
_text = text;
}
public bool WriteToFile()
{
try
{
using (System.IO.StreamWriter WriteToFile = new System.IO.StreamWriter(FileName))
{
WriteToFile.Write(_text);
WriteToFile.Close();
}
return true;
}
catch
{
return false;
}
}
}
Without actually showing you the code I'll try and explain getters and setters so you can understand their concept.
A property looks like a method to the internal class and field to an external class.
E.g. You are able to perform logic in your property whereas when you call the property from a different class it behaves just like any other field.
GET: Used to retrieve and return a property. You are able to perform some complex logic before actually returning your property. You are able to safely expose private variables via the Get without compromising on writing.
SET: Used to set the value of a property that may be private, constant or public. You are able to have control over the setting of the variable.
Usually properties are used to keep values as attributes; characteristics; settings.
Methods and functions you would think as actions.
e.g as shown below:
public class MyClass{
/// <summary>
/// Keeps the file name
/// </summary>
public string FileName { get; set; }
/// <summary>
/// Action to write the file
/// </summary>
/// <returns>Returns true if the info. was wrote into the file.</returns>
public bool WriteToFileSucceed()
{
try
{
using (System.IO.StreamWriter WriteToFile = new System.IO.StreamWriter(FileName))
{
WriteToFile.Write(text);
WriteToFile.Close();
}
return true;
}
catch
{
return false;
}
}}
...
public void button1_Click(object sender, EventArgs e){
MyClass myClass = new MyClass();
myClass.FileName = #"C:\crypt\crypt.txt";
if(myClass.WriteToFileSucceed())
{
MessageBox.Show("Success, managed to write to the file");
}
else
{
MessageBox.Show("Ops! Unable to write to the file.");
}}

Public variable invoking incorrect result

public partial class ThanglishToTamilGUI : Form
{
public string anz;
public ThanglishToTamilGUI()
{
InitializeComponent();
}
public void btnConvertToBraille_Click(object sender, EventArgs e)
{
anz = richTextBoxTamil.Text.ToString();
GUI.TamilToBrailleGUI c1 = new GUI.TamilToBrailleGUI();
c1.Visible = true;
}
}
I need to pass my richtextbox (richTextBoxTamil) content to variable call anz.
I am retrriving anz variable in other form as form load event:
private void TamilToBrailleGUI_Load(object sender, EventArgs e)
{
ThanglishToTamilGUI tt = new ThanglishToTamilGUI();
String apper = tt.anz;
richTextBoxTamil.Text = apper;
}
My Problem:
I am getting null values as result. Since if I assigned any values that invoked correctly.
public partial class ThanglishToTamilGUI : Form
{
public string anz = "Hai";
public ThanglishToTamilGUI()
{
InitializeComponent();
} ...
Here my ans value is passed as "Hai". But my requirement is to get what ever the content in the richTextBoxTamil and pass it to that public variable call anz. What went wrong here please help me.
Thank you.
This is the problem:
ThanglishToTamilGUI tt = new ThanglishToTamilGUI();
String apper = tt.anz;
How do you expect apper to ever be anything other than null? You're fetching the variable from a freshly-created form, which has never been shown, and which has never had btnConvertToBraille_Click called on it.
Presumably there's an existing ThanglishToTamilGUI object somewhere, and that's the one you want to fetch the variable from. Basically, one form needs to know about the instance of the other form.
(I'd also strongly suggest using a property rather than a public variable, but that's a different matter. You might not even need to have a separate variable at all - just declare a property which fetches richTextBoxTamil.Text.)
Alternatively, just pass the relevant string to the constructor of the new form:
public void btnConvertToBraille_Click(object sender, EventArgs e)
{
GUI.TamilToBrailleGUI c1 = new GUI.TamilToBrailleGUI(richTextBoxTamil.Text);
c1.Visible = true;
}
Then the new form doesn't need to know about the old form at all - it only needs to know the text to display.
(You might want to pull it out of the constructor and into a settable property, but it's the same basically principle: the code creating the form pushes the data, rather than the new form pulling it.)
You can create a public property to access the current Text value of the textbox.
public string RichTextBoxText
{
get
{
return richTextBoxTamil.Text;
}
}
The way you do it now the form is instantiated, but the click event is not fired. So there's no way you will get anything other than what you initialized the field to.
Load is not the place to look for user input. An event (like click) is where you need to check the property value:
private void SomeClick(object sender, EventArgs e)
{
String result = thanglishToTamilGUIObject.RichTextBoxText;
//do something with text
}

Set Method isn't working... it doesn't give the value to the variable

Hell guys.
I am making this project with a Server, a Client and a Class library.
In the class library (which I added to the Server and the Client as Reference), I have for example an:
string f = "not working";
public void SetString(string n)
{
f = n;
}
public string GetStr ()
{
return f;
}
I have connected the client and the server and they are working properly, also the Get method is working but the SET METHOD isn't working?? When I call the set method from the client, it doesn't set the value that I am giving!!.
HttpChannel chan = new HttpChannel();
Tic obj = (Tic)Activator.GetObject(typeof(Tic), "http://127.0.0.1:9050/MyServer");
private void Form1_Load(object sender, EventArgs e)
{
ChannelServices.RegisterChannel(chan);
}
private void button1_Click(object sender, EventArgs e)
{
string m = "working";
obj.SetString(m);
}
Again i repeat that the Get Method is working properly, but only the Set Method... and the problem is that it doesn't show me any error!!! it is just not giving the value to the string variable!!
If I understand your set up correctly you are contacting a remote http server and calling a method which sets a variable value. You then contact that http server and ask for the value back, and you are getting the original value.
I'm not sure what sort of web "server" you are hosting but most of the time, servers only instantiate their classes when called upon. So basically you are contacting a server, it instantiates whatever class containing the "f" string. You set the value. The server completes its job and kills the process. Then you contact the server again asking for the value of "f", so it instantiates everything again, which means the value would be "not working".
Have you tried using Properties instead?
public class Foo
{
public string Message {get;set;}
}
public class Bar
{
public void Boz()
{
var foo = new Foo();
foo.Message = "Working";
}
}

Null Exception in Program

I have a program like this
class Program
{
static void Main(string[] args)
{
test objtest = new test();
objtest.Name = "vikas";
Test(objtest);
//objtest = null; when I uncomment this line it shows me exception
Console.WriteLine(objtest.Name);
Console.ReadLine();
}
private static void Test(test objtest)
{
objtest.Name = "chetan";
objtest = null;
}
}
class test
{
private string _Name = string.Empty;
public string Name
{
get
{
return _Name;
}
set
{
_Name = value;
}
}
}
Output:
chetan
Second program:
class Program
{
static void Main(string[] args)
{
test objtest = new test();
objtest.Name = "vikas";
Test(objtest);
objtest = null;
try
{
Console.WriteLine(objtest.Name);
}
catch (Exception ex)
{
Console.WriteLine(ex.InnerException + " " + ex.Message);
}
Console.ReadLine();
}
private static void Test(test objtest)
{
objtest.Name = "chetan";
objtest = null;
}
}
class test
{
private string _Name = string.Empty;
public string Name
{
get
{
return _Name;
}
set
{
_Name = value;
}
}
}
Output:
Object reference not to set an instance of object
Why?
When I set objtest = null; in Test it shows me the value, but when I set null in same it shows me error.
Added after #kmatyaszek post:
In first program
static void Main(string[] args)
{
test objtest = new test();
objtest.Name = "vikas"; // **I am assigning this value**
Test(objtest);
//objtest = null; when I uncomment this line it shows me exception
Console.WriteLine(objtest.Name);
Console.ReadLine();
}
private static void Test(test objtest)
{
objtest.Name = "chetan";
objtest = null;
}
Why it is displaying "chetan" not "vikas"??
Classic confusion caused by reference type that is being passed by value.
I will give a rather short and simple answer here; those interested to learn more and in depth are more than welcome to read Jon Skeet article on Parameter passing in C# and similar article with diagrams, by Lee Richardson.
Reference type, in short, is any type that is not primitive or struct. Any custom defined class is hence a reference type.
When instance of such class is passed to a function, what actually happens is that a pointer to this instance is passed. More accurately, a copy of the pointer is being passed since by default parameters are passed by value.
When you have this line:
test objtest = new test();
New instance of the class test is being created and assigned address in the memory. Every time you refer to the variable objtest, that address will be used for example:
objtest.Name = "vikas";
The runtime engine will go the address assigned when the instance was created, look for the place reserved for the property Name and change the contents there to "vikas". The change is immediate and permanent for this instance.
When you have such function signature:
private static void Test(test objtest)
The actual parameter that is passed "behind the scenes" is the address of the instance in the memory. Whenever you refer to the parameter objtest inside the function, the runtime engine will go to the address passed as the actual parameter. So having this line inside the function:
objtest.Name = "chetan";
Is exactly the same as having it outside the function: it will look for the place reserved for the property Name in the memory address passed, and change the contents there to "chetan". Yet again, this change is immediate and permanent for that instance. For this thing (changing properties) it doesn't matter if you're using ref or not, as you are dealing with reference type.
However, being passed by value (e.g. without ref keyword) means that the memory address is being copied and the function only get the copy, very much like passing integer. Any change to the copy will not affect the original value. Thus, when you have this line inside the function:
objtest = null;
You change the copy to point on nothing, however the variable outside the function still point to the same address and won't be null.
If you have such function signature:
private static void Test(ref test objtest)
Then it means the address itself is passed by reference, hence changing the variable holding the address will cause it to be changed outside the function as well.
This pretty much sums it up, I don't bring anything new here just clarifying things with what I deem more simple explanation.
You have problem here with passing parameter to function.
Default parameters are passed by value.
The attempt to reassign the parameter to a different memory location only works inside the method Test and does not affect the original variable objtest in Main method.
So when you add ref to parameter in Test function in two cases behaviour will be the same, because all of the changes that take place inside the method Test affect the original object objtest in Main method.
First example from your question with ref parameter:
class Program
{
static void Main(string[] args)
{
test objtest = new test();
objtest.Name = "vikas";
Test(ref objtest);
//objtest = null; when I uncomment this line it shows me exception
Console.WriteLine(objtest.Name);
Console.ReadLine();
}
private static void Test(ref test objtest)
{
objtest.Name = "chetan";
objtest = null;
}
}
class test
{
private string _Name = string.Empty;
public string Name
{
get
{
return _Name;
}
set
{
_Name = value;
}
}
}
In the second example first you set null to original object and after that you want read property Name, so you will get NullReferenceException.
Well, you're using an object with a value of null, which causes the exception. null for reference types means "points to zero". When you're trying to access the value stored at address zero, you get a NullReferenceException.
You're setting objtest to null before you access the Name property, so you're trying to access the Name property of the object stored at address zero, which makes no sense.

Categories