Являются ли типы значений неизменяемыми по определению?

Я часто читаю этоstructОни должны быть неизменными - не так ли по определению?

Рассматриваете ли выint быть неизменным?

int i = 0;
i = i + 123;

Кажется хорошо - мы получаем новыйint и назначить его обратноi, Как насчет этого?

i++;

Хорошо, мы можем думать об этом как о ярлыке.

i = i + 1;

Что насчетstruct Point?

Point p = new Point(1, 2);
p.Offset(3, 4);

Это действительно изменяет точку(1, 2)? Разве мы не должны думать об этом как о сокращении следующего сPoint.Offset() возвращать новую точку?

p = p.Offset(3, 4);

Основой этой мысли является то, как тип значения без идентичности может быть изменяемым? Вы должны взглянуть на него как минимум дважды, чтобы определить, изменился ли он. Но как вы можете сделать это без личности?

Я не хочу усложнять рассуждения об этом, учитываяref параметры и бокс. Я также знаю, чтоp = p.Offset(3, 4); выражает неизменность гораздо лучше, чемp.Offset(3, 4); делает. Но остается вопрос - не являются ли типы значений неизменяемыми по определению?

ОБНОВИТЬ

Я думаю, что есть как минимум две концепции - изменчивость переменной или поля и изменчивость значения переменной.

public class Foo
{
    private Point point;
    private readonly Point readOnlyPoint;

    public Foo()
    {
        this.point = new Point(1, 2);
        this.readOnlyPoint = new Point(1, 2);
    }

    public void Bar()
    {
        this.point = new Point(1, 2);
        this.readOnlyPoint = new Point(1, 2); // Does not compile.

        this.point.Offset(3, 4); // Is now (4, 6).
        this.readOnlyPoint.Offset(3, 4); // Is still (1, 2).
    }
}

В примере мы имеем поля - изменяемые и неизменяемые. Поскольку поле типа значения содержит все значение, тип значения, хранящийся в неизменяемом поле, также должен быть неизменным. Я все еще весьма удивлен результатом - я не ожидал, что поле readonly останется неизменным.

Переменные (кроме констант) всегда изменяемы, поэтому они не налагают никаких ограничений на изменчивость типов значений.

Ответ, кажется, не так прост, поэтому я перефразирую вопрос.

Учитывая следующее.

public struct Foo
{
    public void DoStuff(whatEverArgumentsYouLike)
    {
        // Do what ever you like to do.
    }

    // Put in everything you like - fields, constants, methods, properties ...
}

Можете ли вы дать законченную версиюFoo и пример использования - который может включать в себяref параметры и бокс - чтобы не было возможности переписать все случаи

foo.DoStuff(whatEverArgumentsYouLike);

с участием

foo = foo.DoStuff(whatEverArgumentsYouLike);