****Just below is my winform client inst with one parameter constructor within the class.****
private void button1_Click(object sender, EventArgs e)
{
string s1 = textBox1.Text;
int x1 = Convert.ToInt32(s1);
int X= x1;
ExternalTest ob = new ExternalTest(X);
string s2 = Convert.ToString(ob.Y);
ob.Y = 0;
textBox2.Text = s2;
And below this is my class that i added to the project
The code below is an added class within the assembly. If i tried to make it a class library and and add addreference - it will not build.
class ExternalTest
{
private int _x;
// protected new int x
// {
// get { return _x; }
// set {_x = value ;}
// }
private int y;
public int Y
{
get {return y = Mult(_x); }
set { }
}
internal int Mult(int _x)
{
y = _x + 51;
return y;
}
public ExternalTest(int X)
{
_x = X;
}
}
}
Your class is not public by default. You must add public to the definition of the class when you're using it in an external library, or the WinForms client will not be able to see it.
EG:
public class ExternalObj
{
// ...
}
Based on the fact that you are getting a compile error only when this class is in an external library, and the numerous times I've forgotten to add public when I've needed it myself, I'm thinking this is probably the issue.
Related
I'm new to learning C# and am trying to implement the below code however, I am unable to do so, receiving the error "A namespace cannot directly contain members such as fields or methods".
namespace Grades
{
public string LetterGrade
{
get
{
string result;
if (RoundResult(AverageGrade) >= 90)
{
result = "A";
}
else if (RoundResult(AverageGrade) >= 80)
{
result = "B";
}
else if (RoundResult(AverageGrade) >= 70)
{
result = "C";
}
else
{
result = "F";
}
return result;
}
}
private double RoundResult(double result)
{
double r;
r = Math.Round(result);
return r;
}
public class GradeStatistics
{
public float AverageGrade = 50;
public float HighestGrade = 78;
public float LowestGrade = 11;
}
}
What I am trying to accomplish is to create a method called "RoundResult" which will round the "AverageGrade" result. I am merely doing this as an experiment to try and understand how methods interact with each other.
The biggest hurdle I am facing while learning C# is in regards to methods and classes, how to use them correctly, when to place them within an existing class or create there own separate class etc. If someone has any recommended resource that goes into extensive step by step detail on how to implement methods and classes, that would be greatly appreciated.
Edit: Thanks to Reputation Farmer and wazdev for their answers. I'd like to add an additional question....
Why is the "GradeStatistic" method a valid method to call the "AverageGrade" from within the same class yet my "RoundResult" method can not be within the same class?
This error message is occurring because you have two methods directly inside your namespace declaration- they need to be wrapped inside a class.
One possible solution is to create a "GradeCalculator" class and put your two methods inside that ... please note that this is not an optimal solution, but I've tried to modify as little as posssible:
namespace Grades
{
public class GradeCalculator
{
public string LetterGrade
{
get
{
string result;
if (RoundResult(GradeStatistics.AverageGrade) >= 90)
{
result = "A";
}
else if (RoundResult(GradeStatistics.AverageGrade) >= 80)
{
result = "B";
}
else if (RoundResult(GradeStatistics.AverageGrade) >= 70)
{
result = "C";
}
else
{
result = "F";
}
return result;
}
}
private double RoundResult(double result)
{
double r;
r = Math.Round(result);
return r;
}
}
public static class GradeStatistics
{
public static float AverageGrade = 50;
public static float HighestGrade = 78;
public static float LowestGrade = 11;
}
}
As the error says, namespace can't contain methods. You should put them inside a class:
namespace Grades
{
public static class GradeUtil {
public static string LetterGrade { ... }
private static double RoundResult(double result) { ... }
}
public class GradeStatistics
{
public float AverageGrade = 50;
public float HighestGrade = 78;
public float LowestGrade = 11;
}
}
Note the word static. It allows you to call a method without object instance. I.e. you can write GradeUtil.LetterGrade .... It's unclear, cut looks like this is what you intended.
I am developing a series of numbers starting from Setstart(2) function from ISeries interface. I tried to implement this interface in Class1 but it threw an error to me. And I am getting stuck at this error and not been able to figure out to fix this. What am I missing? Please help
I tried to make all functions in the interface public
I tried to remove public access specifier from interface
public interface ISeries {
void Setstart (int a);
int GetNext ();
void Reset ();
}
class Class1 : ISeries {
int val;
void Setstart (int a) {
val = a;
}
int GetNext () {
return val++;
}
void Reset () {
val = 0;
}
static void Main () {
Class1 c = new Class1 ();
c.Setstart (2);
Console.WriteLine (c.GetNext ());
c.Reset ();
Console.WriteLine ();
}
}
I expect the output to be 3 and 0 error is being generated
Your should try something like this.
Because you have to play with one variable so you have to make use of ref `keyword in this case.
and also you have to mark all the method inside a class as a public otherwise you were not be able to access those method inside main
Code:
using System;
namespace StackoverflowProblem
{
public interface ISeries
{
void Setstart(ref int value);
int GetNext(ref int value);
void Reset(ref int value);
}
public class Class1 : ISeries
{
public int val { get; set; }
public void Setstart(ref int value)
{
this.val = value;
}
public int GetNext(ref int value)
{
value = value + 1;
this.val = value;
return this.val;
}
public void Reset(ref int value)
{
// Resetting val.
value = 0;
this.val = value;
}
}
class Program
{
static void Main(string[] args)
{
Class1 c = new Class1();
int value = 2;
c.Setstart(ref value);
Console.WriteLine(" " + c.GetNext(ref value));
c.Reset(ref value);
Console.WriteLine();
}
}
}
Output:
val++ will incriment after returning the current value, ++val will increment first then return the value, you should now get 3, also make it proper scoped to access the methods from outside
class Class1 : ISeries {
int val;
public void Setstart (int a) {
val = a;
}
public int GetNext () {
return ++val;
}
public void Reset () {
val = 0;
}
static void Main () {
Class1 c = new Class1();
c.Setstart(2);
Console.WriteLine (c.GetNext());
c.Reset();
Console.WriteLine ("");
}
}
You need to make your methods public to be accessible outside from class which is missing other than that your code looks fine.
You need to make all the 3 methods public as per your scenario like :
public void Setstart (int a) {
and you will need to first add 1 and then return to get 3 as output as val++ will return the current value and then increment it by 1:
public int GetNext () {
// return val++; // Post increment will not work according to question.
val = val + 1;
return val;
}
Your class with complete implementation of Interface would be like following:
public class Class1 : ISeries {
int val;
public void Setstart (int a) {
val = a;
}
public int GetNext () {
val = val + 1;
return val;
}
public void Reset () {
val = 0;
}
}
I am trying to build a unit test.
The class Position is implemented in a third party library. But for my unit test I need the Size property to be set to a specific value.
public class Position
{
private double _size;
private double Size
{
get
{
return _size;
}
internal set
{
_size = value;
}
}
}
I read this post: How do you create a unit-testing stub for an interface containing a read-only member?
but could not figure out how to make it work for me.
This is the class under test (just a simplified example). The posargument in the CalcPositionMetric() method must be of type Position:
public class PositionMetrics
{
public PositionMetrics()
{}
public double CalcPositionMetric(Position pos)
{
return 2 * pos.Size;
}
}
Here is a piece of my unit test:
using NUnit.Framework;
using NMock;
[TestFixture]
public class PositionUnitTests
{
[Test]
public void TestPosition()
{
Mock<Position> tmpPosMock = mFactory.CreateMock<Position>();
tmpPosMock.Expects.One.GetProperty(v => v.Size).WillReturn(7); /* !!! Exception !!! System.ArgumentException : mock object position has a getter for property Size, but it is not virtual or abstract */
/* Execute Test with tmpPositions*/
PositionMetrics pm = new PositionMetrics();
double result = pm.CalcPositionMetric(tmpPosMock.MockObject)
Assert.AreEqual(14, result);
}
}
But as you can see I get an exception. Could somebody help me to resolve this problem? Any other solutions are also welcome!
Cheers
Konstantin
New answer for the updated question I suggest you to introduce some kind of a proxy interface for that. See the code below:
interface IPosition {
int Size { get; }
}
class Position { //in 3rd party lib
public int Size {
get { return 5; }
}
}
class RealPosition : IPosition { //use this as your real object instead of using Position directly
private Position position;
public RealPosition(Position position) {
this.position = position;
}
public int Size {
get { return position.Size; }
}
}
class MockPosition : IPosition { //use this for testing
public int Size{ get; set; }
}
public class Program {
static void Main(string[] args) {
var pos = new MockPosition { Size = 7 };
Console.WriteLine(Calc(pos)); //prints 14
Console.ReadLine();
}
static int Calc(IPosition pos) { //change your method signature to work with interface
return pos.Size * 2;
}
}
Old answer If the class is not sealed you don't need any mocking libraries. Just use the new modifier for the required properties like this:
class Position {
public int Size { get { return 5; } }
}
class MockPosition : Position {
public new int Size { get; set; }
}
....
var mock= new MockPosition();
mock.Size = 7;
To use these items in some sort of list you'll have to cast them like this:
var items = new List<Position>();
for (int i = 0; i < 5; i++) {
items.Add(new MockPosition { Size = i });
}
foreach (var item in items.Cast<MockPosition>()) {
Console.Write("{0}\t", item.Size); //prints 0 1 2 3 4
}
If it is sealed and the property is not virtual than you'll have to use some other techniques, Moq (which I guess you are using) does not allow that
In my program, I am making currency addition from a for...loop. It is working fine. But I am not sure if what has been done is correct and in accordance with C#.
class Program {
private double _amount;
public double amount {
get {
return _amount;
}
set {
_amount = value;
}
}
static void Main(string[] args) {
Program p = new Program();
for (int i = 1000; i < 1300; i++) {
double y = 30.00;
double x = y + p._amount;
p._amount = x;
}
Console.WriteLine(p._amount.ToString());
Console.ReadLine();
}
}
I have reduced the size of the code. In effect, however, there are several if clauses within the for...loop which I do the calculations.
I would like to thank anyone who could point out any inconsistency with C# coding principles.
The first thing is to use meaningful names, so program could be given a more
meaningful name.
Modularise your code (create a separate class from your program) and use the recommended coding practices by MSDN for C#.
class Calculation
{
public double Amount { get; set; }
public double run(double y)
{
// No need to start at 1000.
for(int i = 0; i < 300; i++)
{
Amount += y;
}
return Amount;
}
}
class Program
{
static void Main(string[] args)
{
Calculation calculation = new Calculation();
// pass your variable as a parameter into a class function.
var y = 30.0;
Console.WriteLine(calculation.run(y).ToString());
// Console.ReadLine(); use control F5 to prevent console window from closing.
}
}
C# Coding Conventions (C# Programming Guide)
I would recommend changing this code:
public double amount
{
get
{
return _amount;
}
set
{
_amount = value;
}
}
with this:
public double getamount()
{
return _amount;
}
public void setamount(int value)
{
_amount = value;
}
I'm implementing a union-find data structure in C#. The elements must extend the Element inner-class, but I'd like to to keep the fields in that class private to the outside world. They need to be public to the direct outer-class, however. The folloowing code does not compile due to "inconsistent accessibility":
class DisjointSetForrests<T> where T : DisjointSetForrests<T>.Element {
private class PrivateElement {
public Element p;
public int rank;
}
public class Element : PrivateElement {
}
public void MakeSet(T x) {
x.p = x;
x.rank = 0;
}
public T FindSet(T x) {
if (x != x.p) x.p = FindSet(x);
return (T)x.p;
}
public void Union(T x, T y) {
Link(FindSet(x), FindSet(y));
}
public void Link(T x, T y) {
if (x.rank > y.rank) {
y.p = x;
} else {
x.p = y;
if (x.rank == y.rank) y.rank++;
}
}
}
Is there a way to achieve what I want, or should I accept the fields in Element being public?
It's not possible to keep them only public to the outer class.
The question is why do you need to keep them public? If you creating a library you could use internal.