Questions
-
What is the difference between
ref
andout
?-
ref
variables are “read-only”, their value cannot change inside a method. -
ref
is a keyword,out
is not. - There isn’t any: they are both used to pass a reference to a method.
-
out
variables may not be initialized going into the method, but have to receive a value inside the method. - There isn’t any: they are both used to pass a value to a method.
-
-
What would be displayed by the following?
static void Main(){ int x = 4, y = 3; Console.WriteLine($"x is {x}, y is {y}."); AddR(ref x, ref y); Console.WriteLine($"x is {x}, y is {y}."); } static void AddR(ref int a, ref int b){ int tmp = a; a = a + b; b = tmp - b; }
- “x is {x}, y is {y}.”, “x is {x}, y is {y}.”
- “x is 4, y is 3.”, “x is 3, y is 4.”
- “x is 4, y is 3.”, “x is 4, y is 3.”
- “x is 4, y is 3.”, “x is 7, y is 1.”
- This code would not compile.
-
The following method would not compile. Why?
public static void Test(int a, out int b){ if (a > 0) { b = 12; } }
- A method cannot be
static
and havevoid
as a return type. - Any
out
parameter must have its value set in the body of the method. - The
else
is missing. - The keyword
out
cannot be used in the header of a method. - An
out
parameter cannot be assigned a value.
- A method cannot be
Warm-up Exercises
-
Consider the following code:
using System; class Program { static void Main() { int x = 1; int y = 2; int z; char c = Foo(x, ref y, out z); char d = Foo(x, ref y, out z, '%'); } static char Foo( int x, ref int y, out int z, char symb = '*' ) { x++; y--; z = x + y; return symb; } }
-
What are the values of
x
,y
andz
- Before the
Foo
method is called? - Inside the
Foo
method? - After the
Foo
method executed?
- Before the
-
What is the value of
c
? -
What is the value of
d
?
Solution
Before the
Foo
method is executed: 1, 2, andz
is not set.Inside the
Foo
method: 2, 1 and 3.After the
Foo
method: 1, 0, and 2c
holds'*'
,d
holds%
. -
Problems
-
Write the
AddRev
method (header included) such that the following:int x0 = 4, y0 = 3; AddRev(ref x0, ref y0); Console.WriteLine($"x0 is {x0}, y0 is {y0}.");
would display
x0 is 7, y0 is 1.
Solution
void AddRev(ref int xP0, ref int yP0) { int temp = xP0; xP0 = xP0 + yP0; yP0 = temp - yP0; }
-
Write the
AddLog
method (header included) such that the following:string log; int x1 = 4, y1 = 3; int result = AddLog(x1, y1, out log); Console.WriteLine(log + "\n" + result);
would display
4 + 3 = 7. 7
Solution
int AddLog(int xP1, int yP1, out string logP) { logP = xP1 + " + " + yP1 + " = " + (xP1 + yP1) + "."; return xP1 + yP1; }
-
Write the
AddReset
method (header included) such that the following:int x2 = 2, y2 = 3, z2; AddReset(ref x2, ref y2, out z2); Console.WriteLine($"x2 = {x2}, y2 = {y2}, z2 = {z2}.");
would display
x2 = 0, y2 = 0, z2 = 5.
Solution
void AddReset(ref int xP2, ref int yP2, out int zP2) { zP2 = xP2 + yP2; xP2 = 0; yP2 = 0; }
-
Consider the “regular” implementation of the
Rectangle
class:using System; class Rectangle { private int length; public int Length { get { return length; } set { if (value < 0) { throw new ArgumentNullException(); } else length = value; } } private int width; public int Width { get { return width; } set { if (value < 0) { throw new ArgumentNullException(); } else width = value; } } public Rectangle(int wP, int lP) { Width = wP; Length = lP; } public override string ToString() { return $"Width: {Width}\nLength: {Length}"; } }
And try to answer the following questions.
Solution
A possible solution to those questions is available.
-
Write a
Draw
method that takes one optionalchar
parameter and draw a rectangle of the calling object’s width and length using that character if provided,*
otherwise. If your method is correctly implemented, thenRectangle r0 = new Rectangle(3, 2); r0.Draw(); r0.Draw('-');
should display
*** *** --- ---
Solution
A possible solution is:
public void Draw(char symb = '*') { string drawing = ""; for (int i = 0; i < Length; i++) { for (int j = 0; j < Width; j++) { drawing += symb; } drawing += "\n"; } Console.WriteLine(drawing); }
-
Write a
Copy
method that does not take arguments, and return a copy of the calling object. If your method is correctly implemented, thenRectangle original = new Rectangle(5, 10); Rectangle copy = original.Copy(); Console.WriteLine("Original:\n" + original + "\nCopy:\n"+ copy + "\n"); copy.Length = 12; Console.WriteLine("\nOriginal:\n" + original + "\nCopy:\n" + copy + "\n");
should display
Original: Width: 5 Length: 10 Copy: Width: 5 Length: 10 Original: Width: 5 Length: 10 Copy: Width: 5 Length: 12
If the length of the original object changed after
copy.Length = 12;
was executed, then your method makes a shallow copy instead of a “deep” copy.Solution
A possible solution is:
public Rectangle Copy() { return new Rectangle(Width, Length); }
-
Write an
Equals
method that returntrue
if the calling object and the argument are both non-null rectangles with the same length and width,false
otherwise. If your method is correctly implemented, thenRectangle r1 = new Rectangle(5, 10); Rectangle r2 = new Rectangle(5, 10); Rectangle r3 = null; Rectangle r4 = r1; Rectangle r5 = new Rectangle(10, 5); Console.WriteLine( "r1 and r2 identical: " + r1?.Equals(r2) + "\nr1 and r3 identical: " + r1?.Equals(r3) + "\nr3 and r1 identical: " + r3?.Equals(r1) + "\nr3 and r3 identical: " + r3?.Equals(r3) + "\nr1 and r4 identical: " + r1?.Equals(r4) + "\nr1 and r5 identical: " + r1?.Equals(r5) );
should display
r1 and r2 identical: True r1 and r3 identical: False r3 and r1 identical: r3 and r3 identical: r1 and r4 identical: True r1 and r5 identical: False
Solution
A possible solution is:
public bool Equals(Rectangle rP) { if (rP == null) return false; return rP.Length == Length && rP.Width == Width; }
-