Movatterモバイル変換


[0]ホーム

URL:


Skip to main content

This browser is no longer supported.

Upgrade to Microsoft Edge to take advantage of the latest features, security updates, and technical support.

Download Microsoft EdgeMore info about Internet Explorer and Microsoft Edge
Table of contentsExit focus mode

What's new in C# 12

  • 2024-06-04
Feedback

In this article

C# 12 includes the following new features. You can try these features using the latestVisual Studio 2022 version or the.NET 8 SDK.

C# 12 is supported on.NET 8. For more information, seeC# language versioning.

You can download the latest .NET 8 SDK from the.NET downloads page. You can also downloadVisual Studio 2022, which includes the .NET 8 SDK.

Note

We're interested in your feedback on these features. If you find issues with any of these new features, create anew issue in thedotnet/roslyn repository.

Primary constructors

You can now create primary constructors in anyclass andstruct. Primary constructors are no longer restricted torecord types. Primary constructor parameters are in scope for the entire body of the class. To ensure that all primary constructor parameters are definitely assigned, all explicitly declared constructors must call the primary constructor usingthis() syntax. Adding a primary constructor to aclass prevents the compiler from declaring an implicit parameterless constructor. In astruct, the implicit parameterless constructor initializes all fields, including primary constructor parameters to the 0-bit pattern.

The compiler generates public properties for primary constructor parameters only inrecord types, eitherrecord class orrecord struct types. Nonrecord classes and structs might not always want this behavior for primary constructor parameters.

You can learn more about primary constructors in the tutorial forexploring primary constructors and in the article oninstance constructors.

Collection expressions

Collection expressions introduce a new terse syntax to create common collection values. Inlining other collections into these values is possible using a spread element..e.

Several collection-like types can be created without requiring external BCL support. These types are:

The following examples show uses of collection expressions:

// Create an array:int[] a = [1, 2, 3, 4, 5, 6, 7, 8];// Create a list:List<string> b = ["one", "two", "three"];// Create a spanSpan<char> c  = ['a', 'b', 'c', 'd', 'e', 'f', 'h', 'i'];// Create a jagged 2D array:int[][] twoD = [[1, 2, 3], [4, 5, 6], [7, 8, 9]];// Create a jagged 2D array from variables:int[] row0 = [1, 2, 3];int[] row1 = [4, 5, 6];int[] row2 = [7, 8, 9];int[][] twoDFromVariables = [row0, row1, row2];

Thespread element,..e in a collection expression adds all the elements in that expression. The argument must be a collection type. The following examples show how the spread element works:

int[] row0 = [1, 2, 3];int[] row1 = [4, 5, 6];int[] row2 = [7, 8, 9];int[] single = [.. row0, .. row1, .. row2];foreach (var element in single){    Console.Write($"{element}, ");}// output:// 1, 2, 3, 4, 5, 6, 7, 8, 9,

The spread element evaluates each element of the enumerations expression. Each element is included in the output collection.

You can use collection expressions anywhere you need a collection of elements. They can specify the initial value for a collection or be passed as arguments to methods that take collection types. You can learn more about collection expressions in thelanguage reference article on collection expressions or thefeature specification.

ref readonly parameters

C# addedin parameters as a way to pass readonly references.in parameters allow both variables and values, and can be used without any annotation on arguments.

The addition ofref readonly parameters enables more clarity for APIs that might be usingref parameters orin parameters:

To learn more aboutref readonly parameters, see the article onparameter modifiers in the language reference, or theref readonly parameters feature specification.

Default lambda parameters

You can now define default values for parameters on lambda expressions. The syntax and rules are the same as adding default values for arguments to any method or local function.

You can learn more about default parameters on lambda expressions in the article onlambda expressions.

Alias any type

You can use theusing alias directive to alias any type, not just named types. That means you can create semantic aliases for tuple types, array types, pointer types, or other unsafe types. For more information, see thefeature specification. For an example refactoring walkthrough, seeRefactor your code using alias any type on the .NET blog.

Inline arrays

Inline arrays are used by the runtime team and other library authors to improve performance in your apps. Inline arrays enable a developer to create an array of fixed size in astruct type. A struct with an inline buffer should provide performance characteristics similar to an unsafe fixed size buffer. You likely won't declare your own inline arrays, but you use them transparently when they're exposed asSystem.Span<T> orSystem.ReadOnlySpan<T> objects from runtime APIs.

Aninline array is declared similar to the followingstruct:

[System.Runtime.CompilerServices.InlineArray(10)]public struct Buffer{    private int _element0;}

You use them like any other array:

var buffer = new Buffer();for (int i = 0; i < 10; i++){    buffer[i] = i;}foreach (var i in buffer){    Console.WriteLine(i);}

The difference is that the compiler can take advantage of known information about an inline array. You likely consume inline arrays as you would any other array. For more information on how to declare inline arrays, see the language reference onstruct types.

Experimental attribute

Types, methods, or assemblies can be marked with theSystem.Diagnostics.CodeAnalysis.ExperimentalAttribute to indicate an experimental feature. The compiler issues a warning if you access a method or type annotated with theExperimentalAttribute. All types included in an assembly marked with theExperimental attribute are experimental. You can read more in the article onGeneral attributes read by the compiler, or thefeature specification.

Interceptors

Warning

Interceptors are an experimental feature, available in preview mode with C# 12. The feature may be subject to breaking changes or removal in a future release. Therefore, it is not recommended for production or released applications.

In order to use interceptors, the user project must specify the property<InterceptorsPreviewNamespaces>. This is a list of namespaces which are allowed to contain interceptors.

For example:<InterceptorsPreviewNamespaces>$(InterceptorsPreviewNamespaces);Microsoft.AspNetCore.Http.Generated;MyLibrary.Generated</InterceptorsPreviewNamespaces>

Aninterceptor is a method that can declaratively substitute a call to aninterceptable method with a call to itself at compile time. This substitution occurs by having the interceptor declare the source locations of the calls that it intercepts. Interceptors provide a limited facility to change the semantics of existing code by adding new code to a compilation, for example in a source generator.

You use aninterceptor as part of a source generator to modify, rather than add code to an existing source compilation. The source generator substitutes calls to an interceptable method with a call to theinterceptor method.

If you're interested in experimenting with interceptors, you can learn more by reading thefeature specification. If you use the feature, make sure to stay current with any changes in the feature specification for this experimental feature. If the feature is finalized, we'll add more guidance on this site.

See also

Collaborate with us on GitHub
The source for this content can be found on GitHub, where you can also create and review issues and pull requests. For more information, seeour contributor guide.

Feedback

Was this page helpful?

YesNo

In this article

Was this page helpful?

YesNo