What is the equivalent of Java's final
in C#?
The final
keyword has several usages in Java. It corresponds to both the sealed
and readonly
keywords in C#, depending on the context in which it is used.
Classes
To prevent subclassing (inheritance from the defined class):
Java
public final class MyFinalClass {...}
C#
public sealed class MyFinalClass {...}
Methods
Prevent overriding of a virtual
method.
Java
public class MyClass
{
public final void myFinalMethod() {...}
}
C#
public class MyClass : MyBaseClass
{
public sealed override void MyFinalMethod() {...}
}
As Joachim Sauer points out, a notable difference between the two languages here is that Java by default marks all non-static methods as virtual
, whereas C# marks them as sealed
. Hence, you only need to use the sealed
keyword in C# if you want to stop further overriding of a method that has been explicitly marked virtual
in the base class.
Variables
To only allow a variable to be assigned once:
Java
public final double pi = 3.14; // essentially a constant
C#
public readonly double pi = 3.14; // essentially a constant
As a side note, the effect of the readonly
keyword differs from that of the const
keyword in that the readonly
expression is evaluated at runtime rather than compile-time, hence allowing arbitrary expressions.
readonly
member variables can be modified in constructors: pastebin.com/AzqzYGiA –
Barbet public class MyClass { public sealed override void MyFinalMethod() {...} }
will not compile since there is nothing to override the only way I get this to work is to do something along the lines of: interface IMyClass { void MyFinalMethod(); } public abstract class MyClassSealer : IMyClass { public abstract void MyFinalMethod(); } public class MyClass : MyClassSealer { public sealed override void MyFinalMethod() { } }
(Paste this into an IDE) Is there a better way? –
Anzio non-virtual
by default. As you point out, the sealed
keyword is only permitted for overridden methods and have a very different meaning than non-virtual
. If methods were in fact sealed
by default, then method hiding using the new
keyword wouldn't make sense. –
Sterner final
(assuming the field isn't being initially defined in the constructor,) which is what you're comparing readonly
to. What makes you think it's "common knowledge" when OP didn't even know what the C# equivalent was in the first place? –
Mcleod final
in Java. There is no equivalent in C# - you cannot mark variables inside methods as readonly
in C#. –
Lymph It depends on the context.
- For a
final
class or method, the C# equivalent issealed
. - For a
final
field, the C# equivalent isreadonly
. - For a
final
local variable or method parameter, there's no direct C# equivalent.
For a final local variable or method parameter, there's no direct C# equivalent
a huge distinction. –
Norven const
can only be used on value types. As far as I know there's no way to make an effective constant for a local reference type. –
Bush What everyone here is missing is Java's guarantee of definite assignment for final member variables.
For a class C with final member variable V, every possible execution path through every constructor of C must assign V exactly once - failing to assign V or assigning V two or more times will result in an error.
C#'s readonly keyword has no such guarantee - the compiler is more than happy to leave readonly members unassigned or allow you to assign them multiple times within a constructor.
So, final and readonly (at least with respect to member variables) are definitely not equivalent - final is much more strict.
As mentioned, sealed
is an equivalent of final
for methods and classes.
As for the rest, it is complicated.
For
static final
fields,static readonly
is the closest thing possible. It allows you to initialize the static field in a static constructor, which is fairly similar to static initializer in Java. This applies both to constants (primitives and immutable objects) and constant references to mutable objects.The
const
modifier is fairly similar for constants, but you can't set them in a static constructor.On a field that shouldn't be reassigned once it leaves the constructor,
readonly
can be used. It is not equal though -final
requires exactly one assignment even in constructor or initializer.There is no C# equivalent for a
final
local variable that I know of. If you are wondering why would anyone need it: You can declare a variable prior to an if-else, switch-case or so. By declaring it final, you enforce that it is assigned at most once.Java local variables in general are required to be assigned at least once before they are read. Unless the branch jumps out before value read, a final variable is assigned exactly once. All of this is checked compile-time. This requires well behaved code with less margin for an error.
Summed up, C# has no direct equivalent of final
. While Java lacks some nice features of C#, it is refreshing for me as mostly a Java programmer to see where C# fails to deliver an equivalent.
null
, added final
. If it compiles, I've just made it more clear. If not, I've learned useful information on where it gets reassigned. Then I can ask the harder questions, like: Is this the intended behavior? And if so, how do I clarify that? –
Ultrared Java class final and method final -> sealed. Java member variable final -> readonly for runtime constant, const for compile time constant.
No equivalent for Local Variable final and method argument final
C# constants are declared using the const keyword for compile time constants or the readonly keyword for runtime constants. The semantics of constants is the same in both the C# and Java languages.
sealed
© 2022 - 2024 — McMap. All rights reserved.