What is C# (C-Sharp)?
The C# language was developed within Microsoft primarily by Anders Hejlsberg, Scott Wiltamuth and Peter Golde. Microsoft released the first widely distributed implementation of C# in July 2000 as part of its .NET framework initiative. C# was intended to be a simple, modern and general-purpose programming language that could be used to develop software components for a distributed environment. The newly released C# emphasized source code portability with support for both hosted and embedded systems.
The following figure shows the C# code for a simple console application as it appears in Visual Studio. The application adds together two integers that are entered by the user and then returns the total to the console.
C# provides a basic, readable language for building an application's logic, while hiding much of the underlying complexity of the language's inherent capabilities. The language is currently standardized under the specification ISO/IEC 23270: Information technology -- Programming languages -- C#. The specification was originally based on a submission from Hewlett-Packard, Intel and Microsoft. It is in its third edition, which was released in 2018.
Since its introduction, C# has been widely adopted and is the de facto programming language for most Windows-based development. The language, along with the .NET framework, can also be used to develop applications for systems running Linux, macOS, iOS or Android, although C# is used primarily to develop Windows applications.
C# is considered a strongly typed language, which means that every variable and constant has a type, as do expressions that evaluate to values. The type describes the structure and behavior of the data. This is important when defining and working with variables, which can be thought of as instances of types. C# supports two categories of types:
- Value types. Variables defined with value types contain their data directly -- each variable has its own copy of the data and is isolated from other variables. The operation of one value type variable does not affect other value type variables. C# supports five subcategories of value types: simple types, struct types, enum types, nullable value types and tuple value types.
- Reference types. Variables defined with reference types store only references to their data, which are referred to as objects. Reference types make it possible for two variables to reference the same object, which means that operations on one variable could affect the object being referenced by another variable. C# supports four subcategories of reference types: class types, interface types, array types and delegate types.
When building C# applications, developers can use type declarations to create new types. A type declaration defines the name and members of the new type. Type declarations are based on six of the subcategories available to value and reference types. They include struct types, enum types, tuple value types, class types, interface types and delegate types.
C# and the .NET framework
C# is designed to work with Microsoft's .NET platform, a software ecosystem for developing, compiling and running application code. The platform includes the common language runtime (CLR) and a set of class libraries.
The CLR runs the code and provides services that enable and enhance application development and cross-platform designs. It also offers high-level support for programming languages such as C#, F# and Visual Basic.
When a developer builds a C# application, the source code is compiled into an intermediate language (IL) that conforms to the Common Language Infrastructure standard. The IL code and other application resources are stored in an assembly that is loaded into the CLR when the application runs. The CLR converts the IL code to native machine instructions using a just-in-time compilation process.
The CLR and .NET platform also include features to help streamline and enhance application development:
- Asynchronous code. Provides a simplified approach to asynchronous programming, with code execution based on external resource allocation and task completion.
- Attributes. Enables developers to insert additional descriptive information into metadata that can be extracted using runtime reflection services.
- Code analyzers. Inspects code for quality and style issues.
- Delegates. Defines types that represent references to methods with specific parameter lists and return types.
- Events. Pushes notifications that signal the occurrence of object actions.
- Garbage collection. Manages the allocation and release of an application's memory, eliminating the need for developers to write code to perform memory management.
- Generic types. Enables developers to define type-safe data structures without committing to actual data types.
- Parallel programming. Enables multiple threads to be executed simultaneously to take advantage of a system's processing resources.
- Reflection. Makes it possible to create a type instance dynamically, bind the type to an existing object, or retrieve the type from an object and access its components.
- Type system. Establishes a common type system that defines how types are declared, used and managed, while providing support for type inference.
- Unsafe code. Provides an unsafe context that enables developers to incorporate unverifiable code into their applications. This does not mean that the code is unsafe, only that it cannot be verified like most of the code.
The .NET framework also supports Language-Integrated Query (LINQ), a set of technologies that integrate query capabilities directly into the C# language. In addition to simplifying data access, LINQ offers developers a consistent experience when accessing data from objects, relational databases or Extensible Markup Language resources.
Check out our breakdown of object-oriented programming concepts.