Having a Senior Developer C# Interview? Don't panic, we got you covered! Check that list of 39 top most advanced C# interview questions for experienced developer and got your next six-figure job offer in style!
Object?According to MSDN, "a class or struct definition is like a blueprint that specifies what the type can do. An object is basically a block of memory that has been allocated and configured according to the blueprint. A program may create many objects of the same class. Objects are also called instances, and they can be stored in either a named variable or in an array or collection. Client code is the code that uses these variables to call the methods and access the public properties of the object. In an object-oriented language such as C#, a typical program consists of multiple objects interacting dynamically".
Objects helps us to access the member of a class or struct either they can be fields, methods or properties, by using the dot.
continue and break statements in C#?Exception handling is done using four keywords in C#:
You can store any type of value in the dynamic data type variable. Type checking for these types of variables takes place at run-time.
Boxing and Unboxing both are used for type conversion but have some difference:
Boxing - Boxing is the process of converting a value type data type to the object or to any interface data type which is implemented by this value type. When the CLR boxes a value means when CLR is converting a value type to Object Type, it wraps the value inside a System.Object and stores it on the heap area in application domain.
Unboxing - Unboxing is also a process which is used to extract the value type from the object or any implemented interface type. Boxing may be done implicitly, but unboxing have to be explicit by code.
The concept of boxing and unboxing underlines the C# unified view of the type system in which a value of any type can be treated as an object.
A namespace is designed for providing a way to keep one set of names separate from another. The class names declared in one namespace does not conflict with the same class names declared in another.
namespace SampleNamespace
{
class SampleClass
{
public void SampleMethod()
{
System.Console.WriteLine(
"SampleMethod inside SampleNamespace");
}
}
}Struct and a Class in C#?Class and struct both are the user defined data type but have some major difference:
Struct
System.Value Type.Class
System.Object Type.finally block in C#?Finally block will be executed irrespective of exception. So while executing the code in try block when exception is occurred, control is returned to catch block and at last finally block will be executed. So closing connection to database / releasing the file handlers can be kept in finally block.
There are several ways.
Use ref / out parameters. A return statement can be used for returning only one value from a function. However, using output parameters, you can return two values from a function.
Consider:
private static void Add_Multiply(int a, int b, ref int add, ref int multiply)
{
add = a + b;
multiply = a * b;
}or
private static void Add_Multiply(int a, int b, out int add, out int multiply)
{
add = a + b;
multiply = a * b;
}Another way is to use <Tuple>:
private static Tuple<int, int> Add_Multiply(int a, int b)
{
var tuple = new Tuple<int, int>(a + b, a * b);
return tuple;
}Now that C# 7 has been released, you can use the new included Tuples syntax:
(string, string, string) LookupName(long id) // tuple return type
{
... // retrieve first, middle and last from data storage
return (first, middle, last); // tuple literal
}which could then be used like this:
var names = LookupName(id);
WriteLine($"found {names.Item1} {names.Item3}.");Anonymous types allow us to create a new type without defining them. This is way to defining read only properties into a single object without having to define type explicitly. Here Type is generating by the compiler and it is accessible only for the current block of code. The type of properties is also inferred by the compiler.
Consider:
var anonymousData = new
{
ForeName = "Jignesh",
SurName = "Trivedi"
};
Console.WriteLine("First Name : " + anonymousData.ForeName); Task and Thread in .NETThread represents an actual OS-level thread, with its own stack and kernel resources. Thread allows the highest degree of control; you can Abort() or Suspend() or Resume() a thread, you can observe its state, and you can set thread-level properties like the stack size, apartment state, or culture. ThreadPool is a wrapper around a pool of threads maintained by the CLR.
The Task class from the Task Parallel Library offers the best of both worlds. Like the ThreadPool, a task does not create its own OS thread. Instead, tasks are executed by a TaskScheduler; the default scheduler simply runs on the ThreadPool. Unlike the ThreadPool, Task also allows you to find out when it finishes, and (via the generic Task) to return a result.
Encapsulation is implemented by using access specifiers. An access specifier defines the scope and visibility of a class member.
class ClassA
{
public ClassA() { }
public ClassA(int pValue) { }
}
// client program
class Program
{
static void Main(string[] args)
{
ClassA refA = new ClassA();
}
}Is there a way to modify ClassA so that you can you call the constructor with parameters, when the Main method is called, without creating any other new instances of the ClassA?
The this keyword is used to call other constructors, to initialize the class object. The following shows the implementation:
class ClassA
{
public ClassA() : this(10)
{ }
public ClassA(int pValue)
{ }
}using in C#The reason for the using statement is to ensure that the object is disposed (call IDisposable) as soon as it goes out of scope, and it doesn't require explicit code to ensure that this happens.
The .NET CLR converts:
using (MyResource myRes = new MyResource())
{
myRes.DoSomething();
}to:
{ // Limits scope of myRes
MyResource myRes= new MyResource();
try
{
myRes.DoSomething();
}
finally
{
// Check for a null resource.
if (myRes != null)
// Call the object's Dispose method.
((IDisposable)myRes).Dispose();
}
}A lambda expression is an anonymous function that you can use to create delegates or expression tree types. By using lambda expressions, you can write local functions that can be passed as arguments or returned as the value of function calls. Lambda expressions are particularly helpful for writing LINQ query expressions.
In the following example, the lambda expression x => x * x, which specifies a parameter that's named x and returns the value of x squared, is assigned to a variable of a delegate type:
Func<int, int> square = x => x * x;
Console.WriteLine(square(5));
// Output:
// 25A Destructor is used to clean up the memory and free the resources. But in C# this is done by the garbage collector on its own. System.GC.Collect() is called internally for cleaning up. The answer to second question is "almost never".
Typically one only creates a destructor when your class is holding on to some expensive unmanaged resource that must be cleaned up when the object goes away. It is better to use the disposable pattern to ensure that the resource is cleaned up. A destructor is then essentially an assurance that if the consumer of your object forgets to dispose it, the resource still gets cleaned up eventually.
If you make a destructor be extremely careful and understand how the garbage collector works. Destructors are really weird:
constant and readonly?A const is a compile-time constant whereas readonly allows a value to be calculated at run-time and set in the constructor or field initializer. So, a const is always constant but readonly is read-only once it is assigned.
When to use const or readonly:
const
readonly
App.config, but once it initializes it can't be changedConsider a class defined in AssemblyA.
public class Const_V_Readonly
{
public const int I_CONST_VALUE = 2;
public readonly int I_RO_VALUE;
public Const_V_Readonly()
{
I_RO_VALUE = 3;
}
}AssemblyB references AssemblyA and uses these values in code. When this is compiled,
const value, it is like a find-replace, the value 2 is 'baked into' the AssemblyB's IL. This means that if tomorrow I'll update I_CONST_VALUE to 20 in the future. AssemblyB would still have 2 till I recompile it.readonly value, it is like a ref to a memory location. The value is not baked into AssemblyB's IL. This means that if the memory location is updated, AssemblyB gets the new value without recompilation. So if I_RO_VALUE is updated to 30, you only need to build AssemblyA. All clients do not need to be recompiled.Remember: If you reference a constant from another assembly, its value will be compiled right into the calling assembly. That way when you update the constant in the referenced assembly it won't change in the calling assembly!
There are some differences between Abstract Class and Interface which are listed below:
Consider using abstract classes if :
Consider using interfaces if :
Serializable interface.//Overloading
public class test
{
public void getStuff(int id)
{}
public void getStuff(string name)
{}
}//Overriding
public class test
{
public virtual void getStuff(int id)
{
//Get stuff default location
}
}
public class test2 : test
{
public override void getStuff(int id)
{
//base.getStuff(id);
//or - Get stuff new location
}
}ref and out keywords?ref tells the compiler that the object is initialized before entering the function, while out tells the compiler that the object will be initialized inside the function.So while ref is two-ways, out is out-only.
Consider:
delegate void Printer();
static void Main()
{
List<Printer> printers = new List<Printer>();
int i=0;
for(; i < 10; i++)
{
printers.Add(delegate { Console.WriteLine(i); });
}
foreach (var printer in printers)
{
printer();
}
}This program will output the number 10 ten times.
Here’s why: The delegate is added in the for loop and “reference” (or perhaps “pointer” would be a better choice of words) to i is stored, rather than the value itself. Therefore, after we exit the loop, the variable i has been set to 10, so by the time each delegate is invoked, the value passed to all of them is 10.
In an interface, we have virtual methods that do not have method definition. All the methods are there to be overridden in the derived class. That's why they all are public.
Async/Await work in .NET?Where method work?yield keyword used for in C#?Func<string,string> and delegate?lock statement in C#?Where method in C#. Explain.Rust has been Stack Overflow’s most loved language for four years in a row and emerged as a compelling language choice for both backend and system developers, offering a unique combination of memory safety, performance, concurrency without Data races...
Clean Architecture provides a clear and modular structure for building software systems, separating business rules from implementation details. It promotes maintainability by allowing for easier updates and changes to specific components without affe...
Azure Service Bus is a crucial component for Azure cloud developers as it provides reliable and scalable messaging capabilities. It enables decoupled communication between different components of a distributed system, promoting flexibility and resili...