That's the different between value and reference types in C#.
Console.WriteLine(a.Item1==b.Item1);//Output- False
Here you're comparing two object instances. As for any reference type, the equality operator (unless overriden in that type) does reference comparison.
When you store any value type (e.g. int in your case) in the variable of reference-type (object in your case), you're doing what's named boxing.
Console.WriteLine(a.Equals(b));//Output- True
This is because Equals method is overriden in the Tuple type to check if its content are identical to another tuple. It is calling Equals for each of the items and return true if all of them are equal.
Console.WriteLine(a==b);//Output- False
Again, you have two instances of the Tuple class (any class is a reference type), and that Tuple class doesn't have override for an == operator. Therefore, you're just checking if those two variables containing the same instance.
Tuplehas been mostly obsolete since C# 7 came out more than 6 years ago... especiallyTuple<object ... >. Instead, this should really be aValueTuple<int, int, int>, which you can define like this:var a = (1, 1, 1);