static Equals Method Returning False for Value Types
public static bool EqualsMethod(**ValueType** value1, **ValueType** value2)
bool result = false;
Type t1 = value1.GetType();
Type t2 = value2.GetType();
var i = (**dynamic**)value1;
var j = (**dynamic**)value2;
Can Anyone Please Tell me instead of dynamic. What Can I Use For Unboxing ?. So that it can unbox any primitive datatype. And I should not Use Equals Keyword anywhere in my code. I can use the comparer technique , But It is not working
c#
|
show 2 more comments
public static bool EqualsMethod(**ValueType** value1, **ValueType** value2)
bool result = false;
Type t1 = value1.GetType();
Type t2 = value2.GetType();
var i = (**dynamic**)value1;
var j = (**dynamic**)value2;
Can Anyone Please Tell me instead of dynamic. What Can I Use For Unboxing ?. So that it can unbox any primitive datatype. And I should not Use Equals Keyword anywhere in my code. I can use the comparer technique , But It is not working
c#
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
1
You might want to amend your example because you've put "// True" next to theConsole.WriteLine
in your example. Also, your exampleMain()
method outputstrue
for me.
– John
Nov 1 '18 at 8:30
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
1
UseComparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.
– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46
|
show 2 more comments
public static bool EqualsMethod(**ValueType** value1, **ValueType** value2)
bool result = false;
Type t1 = value1.GetType();
Type t2 = value2.GetType();
var i = (**dynamic**)value1;
var j = (**dynamic**)value2;
Can Anyone Please Tell me instead of dynamic. What Can I Use For Unboxing ?. So that it can unbox any primitive datatype. And I should not Use Equals Keyword anywhere in my code. I can use the comparer technique , But It is not working
c#
public static bool EqualsMethod(**ValueType** value1, **ValueType** value2)
bool result = false;
Type t1 = value1.GetType();
Type t2 = value2.GetType();
var i = (**dynamic**)value1;
var j = (**dynamic**)value2;
Can Anyone Please Tell me instead of dynamic. What Can I Use For Unboxing ?. So that it can unbox any primitive datatype. And I should not Use Equals Keyword anywhere in my code. I can use the comparer technique , But It is not working
c#
c#
edited Nov 2 '18 at 4:57
nuli bunny
asked Nov 1 '18 at 8:22
nuli bunnynuli bunny
74
74
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
1
You might want to amend your example because you've put "// True" next to theConsole.WriteLine
in your example. Also, your exampleMain()
method outputstrue
for me.
– John
Nov 1 '18 at 8:30
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
1
UseComparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.
– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46
|
show 2 more comments
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
1
You might want to amend your example because you've put "// True" next to theConsole.WriteLine
in your example. Also, your exampleMain()
method outputstrue
for me.
– John
Nov 1 '18 at 8:30
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
1
UseComparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.
– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
1
1
You might want to amend your example because you've put "// True" next to the
Console.WriteLine
in your example. Also, your example Main()
method outputs true
for me.– John
Nov 1 '18 at 8:30
You might want to amend your example because you've put "// True" next to the
Console.WriteLine
in your example. Also, your example Main()
method outputs true
for me.– John
Nov 1 '18 at 8:30
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
1
1
Use
Comparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46
Use
Comparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46
|
show 2 more comments
4 Answers
4
active
oldest
votes
Equality for primitive types (native to the CLR, like int
) is implemented with CIL instructions. The default equality for value types is done by reflection (which is why struct types should provide their own equality).
System.ValueType
is a reference type, in order for it to work as a base type for other types. Thus, any struct you pass to a ValueType
parameter is boxed, and calling the ==
operator on them does a reference comparison, as you've noticed.
If you want to pass in structs without boxing, you can use generics and the where T : struct
constraint.
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method ofValueType
(i.e. something similar tovalue1.Equals(value2)
). That will determine value equality instead of reference equality.
– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
add a comment |
Building on @jan.h's answer, I would suggest using:
public static bool EqualsMethod<T>(T value1, T value2) where T: struct
return value1.Equals(value2);
as a starting point. By constraining to value types (T: struct
) then this should meet your requirements.
This is OK, but it will always boxvalue2
, even if it can resolve that it can use static-call for thevalue1.Equals
. It may also boxvalue1
if that isn't the case. There's a much better approach (see my answer).
– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
add a comment |
You can directly use ToString() method from object class, rather than unboxing and storing it in another variable.
eg: value1.ToString() && value2.ToString()
1
That's not great;ToString()
is expensive, and is not necessarily at all related to conceptual equality
– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);ToString()
is not; also, you have no clue whatToString()
is going to return in the general case - there is no requirement whatsoever forToString()
to have equality semantics
– Marc Gravell♦
Nov 13 '18 at 9:59
add a comment |
EqualityComparer<T>
already has you covered:
public static bool EqualsMethod<T>(T value1, T value2)
=> EqualityComparer<T>.Default.Equals(value1, value2);
By using generics, this works for any T
- and in the case of value-type T
, it will work without boxing or unboxing. The implementation of .Default
here is clever, and has separate implementations for:
- reference types
- naked value types
Nullable<T>
value types
with each implementation doing "the right thing". It also makes use of the IEquatable<T>
interface where supported, dropping to .Equals(object)
as a fallback.
So: it should do the right thing in all relevant cases. For your own value-types: be sure to implement IEquatable<T>
.
If you want to restrict it to just value-types, add a where T : struct
clause, but ... that doesn't seem necessary or useful here.
add a comment |
Your Answer
StackExchange.ifUsing("editor", function ()
StackExchange.using("externalEditor", function ()
StackExchange.using("snippets", function ()
StackExchange.snippets.init();
);
);
, "code-snippets");
StackExchange.ready(function()
var channelOptions =
tags: "".split(" "),
id: "1"
;
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function()
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled)
StackExchange.using("snippets", function()
createEditor();
);
else
createEditor();
);
function createEditor()
StackExchange.prepareEditor(
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader:
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
,
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
);
);
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function ()
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53097503%2fstatic-equals-method-returning-false-for-value-types%23new-answer', 'question_page');
);
Post as a guest
Required, but never shown
4 Answers
4
active
oldest
votes
4 Answers
4
active
oldest
votes
active
oldest
votes
active
oldest
votes
Equality for primitive types (native to the CLR, like int
) is implemented with CIL instructions. The default equality for value types is done by reflection (which is why struct types should provide their own equality).
System.ValueType
is a reference type, in order for it to work as a base type for other types. Thus, any struct you pass to a ValueType
parameter is boxed, and calling the ==
operator on them does a reference comparison, as you've noticed.
If you want to pass in structs without boxing, you can use generics and the where T : struct
constraint.
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method ofValueType
(i.e. something similar tovalue1.Equals(value2)
). That will determine value equality instead of reference equality.
– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
add a comment |
Equality for primitive types (native to the CLR, like int
) is implemented with CIL instructions. The default equality for value types is done by reflection (which is why struct types should provide their own equality).
System.ValueType
is a reference type, in order for it to work as a base type for other types. Thus, any struct you pass to a ValueType
parameter is boxed, and calling the ==
operator on them does a reference comparison, as you've noticed.
If you want to pass in structs without boxing, you can use generics and the where T : struct
constraint.
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method ofValueType
(i.e. something similar tovalue1.Equals(value2)
). That will determine value equality instead of reference equality.
– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
add a comment |
Equality for primitive types (native to the CLR, like int
) is implemented with CIL instructions. The default equality for value types is done by reflection (which is why struct types should provide their own equality).
System.ValueType
is a reference type, in order for it to work as a base type for other types. Thus, any struct you pass to a ValueType
parameter is boxed, and calling the ==
operator on them does a reference comparison, as you've noticed.
If you want to pass in structs without boxing, you can use generics and the where T : struct
constraint.
Equality for primitive types (native to the CLR, like int
) is implemented with CIL instructions. The default equality for value types is done by reflection (which is why struct types should provide their own equality).
System.ValueType
is a reference type, in order for it to work as a base type for other types. Thus, any struct you pass to a ValueType
parameter is boxed, and calling the ==
operator on them does a reference comparison, as you've noticed.
If you want to pass in structs without boxing, you can use generics and the where T : struct
constraint.
answered Nov 1 '18 at 10:20
jan.hjan.h
511511
511511
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method ofValueType
(i.e. something similar tovalue1.Equals(value2)
). That will determine value equality instead of reference equality.
– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
add a comment |
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method ofValueType
(i.e. something similar tovalue1.Equals(value2)
). That will determine value equality instead of reference equality.
– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
Thank you so much. That was a really helpful answer. But I dont want to pass in structs and want to use class only without using generics. so, Instead of System.ValueType what should I use ?. @jan.h
– nuli bunny
Nov 1 '18 at 10:38
You could use the Equals() method of
ValueType
(i.e. something similar to value1.Equals(value2)
). That will determine value equality instead of reference equality.– jan.h
Nov 1 '18 at 10:47
You could use the Equals() method of
ValueType
(i.e. something similar to value1.Equals(value2)
). That will determine value equality instead of reference equality.– jan.h
Nov 1 '18 at 10:47
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
No We Should not at all use Equals or Reference Equals Methods. Thats where the problem is.. Just here public static bool EqualsMethod(ValueType value1, ValueType value2) instead of valuetype keyword what shoud i use, so that it will accept all primitive types . @jan.h
– nuli bunny
Nov 1 '18 at 10:49
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
Then write your own reflection-based equality method. It's not terribly difficult, even with the public reflection API. But at some point you'll probably need to use Equals.
– jan.h
Nov 1 '18 at 10:57
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
But I am beginner , So I don't know how to use Reflections..Please help me out @jan.h
– nuli bunny
Nov 1 '18 at 11:33
add a comment |
Building on @jan.h's answer, I would suggest using:
public static bool EqualsMethod<T>(T value1, T value2) where T: struct
return value1.Equals(value2);
as a starting point. By constraining to value types (T: struct
) then this should meet your requirements.
This is OK, but it will always boxvalue2
, even if it can resolve that it can use static-call for thevalue1.Equals
. It may also boxvalue1
if that isn't the case. There's a much better approach (see my answer).
– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
add a comment |
Building on @jan.h's answer, I would suggest using:
public static bool EqualsMethod<T>(T value1, T value2) where T: struct
return value1.Equals(value2);
as a starting point. By constraining to value types (T: struct
) then this should meet your requirements.
This is OK, but it will always boxvalue2
, even if it can resolve that it can use static-call for thevalue1.Equals
. It may also boxvalue1
if that isn't the case. There's a much better approach (see my answer).
– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
add a comment |
Building on @jan.h's answer, I would suggest using:
public static bool EqualsMethod<T>(T value1, T value2) where T: struct
return value1.Equals(value2);
as a starting point. By constraining to value types (T: struct
) then this should meet your requirements.
Building on @jan.h's answer, I would suggest using:
public static bool EqualsMethod<T>(T value1, T value2) where T: struct
return value1.Equals(value2);
as a starting point. By constraining to value types (T: struct
) then this should meet your requirements.
answered Nov 1 '18 at 11:46
mjwillsmjwills
15.3k42439
15.3k42439
This is OK, but it will always boxvalue2
, even if it can resolve that it can use static-call for thevalue1.Equals
. It may also boxvalue1
if that isn't the case. There's a much better approach (see my answer).
– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
add a comment |
This is OK, but it will always boxvalue2
, even if it can resolve that it can use static-call for thevalue1.Equals
. It may also boxvalue1
if that isn't the case. There's a much better approach (see my answer).
– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
This is OK, but it will always box
value2
, even if it can resolve that it can use static-call for the value1.Equals
. It may also box value1
if that isn't the case. There's a much better approach (see my answer).– Marc Gravell♦
Nov 13 '18 at 9:57
This is OK, but it will always box
value2
, even if it can resolve that it can use static-call for the value1.Equals
. It may also box value1
if that isn't the case. There's a much better approach (see my answer).– Marc Gravell♦
Nov 13 '18 at 9:57
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
Thanks @MarcGravell.
– mjwills
Nov 13 '18 at 9:59
add a comment |
You can directly use ToString() method from object class, rather than unboxing and storing it in another variable.
eg: value1.ToString() && value2.ToString()
1
That's not great;ToString()
is expensive, and is not necessarily at all related to conceptual equality
– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);ToString()
is not; also, you have no clue whatToString()
is going to return in the general case - there is no requirement whatsoever forToString()
to have equality semantics
– Marc Gravell♦
Nov 13 '18 at 9:59
add a comment |
You can directly use ToString() method from object class, rather than unboxing and storing it in another variable.
eg: value1.ToString() && value2.ToString()
1
That's not great;ToString()
is expensive, and is not necessarily at all related to conceptual equality
– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);ToString()
is not; also, you have no clue whatToString()
is going to return in the general case - there is no requirement whatsoever forToString()
to have equality semantics
– Marc Gravell♦
Nov 13 '18 at 9:59
add a comment |
You can directly use ToString() method from object class, rather than unboxing and storing it in another variable.
eg: value1.ToString() && value2.ToString()
You can directly use ToString() method from object class, rather than unboxing and storing it in another variable.
eg: value1.ToString() && value2.ToString()
answered Nov 13 '18 at 9:51
Swathi AdariSwathi Adari
13
13
1
That's not great;ToString()
is expensive, and is not necessarily at all related to conceptual equality
– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);ToString()
is not; also, you have no clue whatToString()
is going to return in the general case - there is no requirement whatsoever forToString()
to have equality semantics
– Marc Gravell♦
Nov 13 '18 at 9:59
add a comment |
1
That's not great;ToString()
is expensive, and is not necessarily at all related to conceptual equality
– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);ToString()
is not; also, you have no clue whatToString()
is going to return in the general case - there is no requirement whatsoever forToString()
to have equality semantics
– Marc Gravell♦
Nov 13 '18 at 9:59
1
1
That's not great;
ToString()
is expensive, and is not necessarily at all related to conceptual equality– Marc Gravell♦
Nov 13 '18 at 9:53
That's not great;
ToString()
is expensive, and is not necessarily at all related to conceptual equality– Marc Gravell♦
Nov 13 '18 at 9:53
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
but we can directly compare the content by using ToString() rather than unboxing. @Marc Gravell
– Swathi Adari
Nov 13 '18 at 9:58
unboxing is usually free (in terms of allocations - it is boxing that is expensive);
ToString()
is not; also, you have no clue what ToString()
is going to return in the general case - there is no requirement whatsoever for ToString()
to have equality semantics– Marc Gravell♦
Nov 13 '18 at 9:59
unboxing is usually free (in terms of allocations - it is boxing that is expensive);
ToString()
is not; also, you have no clue what ToString()
is going to return in the general case - there is no requirement whatsoever for ToString()
to have equality semantics– Marc Gravell♦
Nov 13 '18 at 9:59
add a comment |
EqualityComparer<T>
already has you covered:
public static bool EqualsMethod<T>(T value1, T value2)
=> EqualityComparer<T>.Default.Equals(value1, value2);
By using generics, this works for any T
- and in the case of value-type T
, it will work without boxing or unboxing. The implementation of .Default
here is clever, and has separate implementations for:
- reference types
- naked value types
Nullable<T>
value types
with each implementation doing "the right thing". It also makes use of the IEquatable<T>
interface where supported, dropping to .Equals(object)
as a fallback.
So: it should do the right thing in all relevant cases. For your own value-types: be sure to implement IEquatable<T>
.
If you want to restrict it to just value-types, add a where T : struct
clause, but ... that doesn't seem necessary or useful here.
add a comment |
EqualityComparer<T>
already has you covered:
public static bool EqualsMethod<T>(T value1, T value2)
=> EqualityComparer<T>.Default.Equals(value1, value2);
By using generics, this works for any T
- and in the case of value-type T
, it will work without boxing or unboxing. The implementation of .Default
here is clever, and has separate implementations for:
- reference types
- naked value types
Nullable<T>
value types
with each implementation doing "the right thing". It also makes use of the IEquatable<T>
interface where supported, dropping to .Equals(object)
as a fallback.
So: it should do the right thing in all relevant cases. For your own value-types: be sure to implement IEquatable<T>
.
If you want to restrict it to just value-types, add a where T : struct
clause, but ... that doesn't seem necessary or useful here.
add a comment |
EqualityComparer<T>
already has you covered:
public static bool EqualsMethod<T>(T value1, T value2)
=> EqualityComparer<T>.Default.Equals(value1, value2);
By using generics, this works for any T
- and in the case of value-type T
, it will work without boxing or unboxing. The implementation of .Default
here is clever, and has separate implementations for:
- reference types
- naked value types
Nullable<T>
value types
with each implementation doing "the right thing". It also makes use of the IEquatable<T>
interface where supported, dropping to .Equals(object)
as a fallback.
So: it should do the right thing in all relevant cases. For your own value-types: be sure to implement IEquatable<T>
.
If you want to restrict it to just value-types, add a where T : struct
clause, but ... that doesn't seem necessary or useful here.
EqualityComparer<T>
already has you covered:
public static bool EqualsMethod<T>(T value1, T value2)
=> EqualityComparer<T>.Default.Equals(value1, value2);
By using generics, this works for any T
- and in the case of value-type T
, it will work without boxing or unboxing. The implementation of .Default
here is clever, and has separate implementations for:
- reference types
- naked value types
Nullable<T>
value types
with each implementation doing "the right thing". It also makes use of the IEquatable<T>
interface where supported, dropping to .Equals(object)
as a fallback.
So: it should do the right thing in all relevant cases. For your own value-types: be sure to implement IEquatable<T>
.
If you want to restrict it to just value-types, add a where T : struct
clause, but ... that doesn't seem necessary or useful here.
answered Nov 13 '18 at 9:56
Marc Gravell♦Marc Gravell
783k19521402549
783k19521402549
add a comment |
add a comment |
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function ()
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53097503%2fstatic-equals-method-returning-false-for-value-types%23new-answer', 'question_page');
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Can you provide an Minimal, Complete, and Verifiable example? As in, value types where this fails?
– John
Nov 1 '18 at 8:27
int i=12 and int j=12. When I pass them to equals method .. as both the values are equal, .. it should return true. But It is returning False.@john
– nuli bunny
Nov 1 '18 at 8:29
1
You might want to amend your example because you've put "// True" next to the
Console.WriteLine
in your example. Also, your exampleMain()
method outputstrue
for me.– John
Nov 1 '18 at 8:30
Ya It is returning True... But I used a dynamic Keyword in my code... So instead of using dynamic , I want to use another keyword or anyother process.Please Help@john
– nuli bunny
Nov 1 '18 at 8:34
1
Use
Comparer.Default.Compare(value1, value2) == 0
to compare instead of your whole method. I know that that is not exactly the same for all cases, but for built-in value types it should be.– Lasse Vågsæther Karlsen
Nov 1 '18 at 8:46