Как я могу установить значение параметра по умолчанию для типа BigInteger? - PullRequest
3 голосов
/ 24 сентября 2011

Мне нужен класс с конструктором типа BigInteger.Я хотел бы установить значение по умолчанию 0 для этого кода, но я получил ошибку компиляции.

public class Hello
{
    BigInteger X {get; set;}
    public Hello(BigInteger x = 0)
    {
        X = x;
    }
}

public class MyClass
{
    public static void RunSnippet()
    {
        var h = new Hello(); // Error <-- 

Что не так?Есть ли способ установить значение по умолчанию для параметра BigInteger?

Ответы [ 4 ]

6 голосов
/ 24 сентября 2011

Параметры по умолчанию работают только с константами времени компиляции (и типами значений, где параметр может быть default(ValType) или new ValType()), и поэтому не работают для BigInteger.Для вашего случая вы могли бы сделать что-то подобное;обеспечивая перегрузку конструктора, которая принимает int, и make с параметром по умолчанию:

public Hello(int x = 0) : this(new BigInteger(x)) {}
public Hello(BigInteger x) 
{
    X = x;
}

В случае, если вам интересно, x = 0 не считается константой, когда тип является BigIntegerпотому что преобразование 0 в BigInteger будет включать вызов оператора неявного преобразования int в BigInteger .

2 голосов
/ 25 сентября 2011

В данном конкретном случае, поскольку требуемое значение по умолчанию равно нулю, вы можете использовать конструктор BigInteger по умолчанию, поскольку BigInteger является типом значения:

public class Hello
{
    BigInteger X { get; set; }

    public Hello(BigInteger x = new BigInteger())
    {
        X = x;
    }
}

Это не будет работать со значениями, кроме нуля, потому что выражение должно быть постоянной времени компиляции :

Каждый необязательный параметр имеет значение по умолчанию как часть его определения. Если для этого параметра не передается аргумент, используется значение по умолчанию. Значением по умолчанию должен быть один из следующих типов выражений:

  • константное выражение;
  • выражение в форме new ValType (), где ValType является типом значения, таким как enum или struct;
  • выражение формы по умолчанию (ValType), где ValType - тип значения.
2 голосов
/ 24 сентября 2011

Использовать перегруженный конструктор

public class Hello
{
    BigInteger X {get; set;}
    public Hello(BigInteger x)
    {
        X = x;
    }
    public Hello()
    {
        X = new BigInteger(0);
    }
}
0 голосов
/ 25 сентября 2011

Из §10.6.1 спецификации C # 4:

Выражение в аргументе по умолчанию должно быть одним из следующих:

  • a константа-выражение
  • выражение вида new S(), где S - тип значения
  • выражение выраженияform default(S), где S - тип значения

* Выражение должно быть неявно конвертируемым с помощью преобразования идентификатора или значения NULL в тип параметра.

Что означает для BigInteger то, что единственным параметром для аргумента по умолчанию является использование 0, выраженного как new BigInteger() или default(BigInteger).

BigInteger x = 0 не работает,потому что 0 имеет тип int, и неявное преобразование из int в BigInteger не является «преобразованием идентификатора или обнуляемым значением».

Если вы хотите, чтобы аргумент по умолчанию был чем-то другим, кроме0, у вас есть несколько вариантов:

  • использовать BigInteger?, пусть по умолчанию будет null и в начале метода chспасибо за это.Если параметр null, установите для него значение по умолчанию.
  • создайте еще одну перегрузку метода, которая принимает, например, int с указанным аргументом по умолчанию.Этот метод в свою очередь вызывает перегрузку BigInteger, которая не имеет аргумента по умолчанию.Это предполагает, что значение по умолчанию вписывается в int, но я думаю, что так должно быть в большинстве случаев.
...