Как «редактировать» внешний объект в функции - PullRequest
1 голос
/ 09 августа 2011

У меня есть этот код:

CreaPager(m_oPacchettiEnum, 1, 10);

private void CreaPager(IEnumerable enPass, int limiteUp, int limiteDown)
{
    enPass= enPass.Skip(limiteDown).Take(limiteUp);
}

и я хотел бы, чтобы при редактировании enPass отразить редактирование в m_oPacchettiEnum без функции возврата IEnumerable<T>.

Итак, отредактируйте напрямую m_oPacchettiEnum с помощью функции. Я делаю это на C, не знаю, возможно ли это на C # (но я так думаю).

Я прочитал кое-что об использовании out, но кажется, что он не работает:

CreaPager(out m_oPacchettiEnum, 1, 10);

private void CreaPager(out IEnumerable enPass, int limiteUp, int limiteDown)
{
    enPass= enPass.Skip(limiteDown).Take(limiteUp);
}

Ответы [ 3 ]

4 голосов
/ 09 августа 2011

out здесь не работает, потому что вы не можете использовать параметр out в методе, пока он не будет назначен. Поскольку ваше назначение использует enum (которое вы должны переименовать) как часть правой части, это не разрешено. Переключение out на ref заставит все работать.

Однако . Как я уже упоминал в своем ответе на ваш предыдущий (теперь удаленный) вопрос, пожалуйста, не делайте этого. Это намного более идиоматично при работе с последовательностями для возврата нового IEnumerable<T>:

var newQuery = CreaPager(m_oPacchettiEnum, 1, 10);

private void CreaPager<T>(IEnumerable<T> enumeration, int limiteUp, int limiteDown)
{
    return enumeration.Skip(limiteDown).Take(limiteUp);
}

Кроме того, вы можете сделать метод методом расширения , поставив перед первым параметром this:

private void CreaPager<T>(this IEnumerable<T> enumeration, int limiteUp, int limiteDown) { .. }

Это позволит вам интегрировать ваш метод в цепочку вызовов LINQ-to-Objects:

var query = myEnumerable.Where(x => x.OtherProp == 1).CreaPager(1, 10).Select(x => x.SomeProp);

РЕДАКТИРОВАТЬ : Поскольку вам также необходимо вернуть string, сделайте , что , параметр out:

private void CreaPager<T>(this IEnumerable<T> enumeration, int limiteUp, int limiteDown, out string myString)
{
    myString = "foo";
    return enumeration.Skip(limiteDown).Take(limiteUp);
}

Вы бы назвали метод следующим образом:

string theString;
var newQuery = CreaPager(m_oPacchettiEnum, 1, 10, out theString);

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

4 голосов
/ 09 августа 2011

Используйте ref вместо out:

CreaPager(ref m_oPacchettiEnum, 1, 10);

private void CreaPager(ref IEnumerable enum, int limiteUp, int limiteDown)
{
    enum = enum.Skip(limiteDown).Take(limiteUp);
}
2 голосов
/ 09 августа 2011

@ Серж ответ будет работать, но не лучше ли это сделать

IEnumerable pager = CreaPager(m_oPacchetti, 1, 10);

private IEnumerable CreaPager(IEnumerable pachetti, int limiteUp, in limiteDown)
{
    return pachetti.Skip(limiteDown).Take(limiteUp - limiteDown);
}

Таким образом, вы можете повторно использовать m_oPachetti, избегая неприятных ссылок и код легче читается.

РЕДАКТИРОВАТЬ:

Как насчет того, что "Пейджер" - итальянское существительное ??? Пейджер - это IEnumerable, вы также можете расширить функциональность, вместо передачи строки.

string theString = "TheStringYouNeedToReturn";
Pager<?> pager = new Pager<?>(m_oPacchetti, 1, 10);

private class Pager<T> : List<T>
{
    private Pager(){}

    public Pager(IEnumerable<T> pachetti, 
                   int limiteUp, 
                   int limiteDown, 
                   string aString)
    {
        this.AString = astring;
        this.AddRange(pachetti.Skip(limiteUp).Take(limiteUp - limiteDown);
    }

    public string AString {get; private set;}

}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...