Как найти последний элемент в списке <>?

Ниже приведен фрагмент из моего кода:

public class AllIntegerIDs 
{
    public AllIntegerIDs() 
    {            
        m_MessageID = 0;
        m_MessageType = 0;
        m_ClassID = 0;
        m_CategoryID = 0;
        m_MessageText = null;
    }

    ~AllIntegerIDs()
    {
    }

    public void SetIntegerValues (int messageID, int messagetype,
        int classID, int categoryID)
    {
        this.m_MessageID = messageID;
        this.m_MessageType = messagetype;
        this.m_ClassID = classID;
        this.m_CategoryID = categoryID;
    }

    public string m_MessageText;
    public int m_MessageID;
    public int m_MessageType;
    public int m_ClassID;
    public int m_CategoryID;
}

Я пытаюсь использовать следующее в моем основном() функциональном коде:

List<AllIntegerIDs> integerList = new List<AllIntegerIDs>();

/* some code here that is ised for following assignments*/
{
   integerList.Add(new AllIntegerIDs());
   index++;
   integerList[index].m_MessageID = (int)IntegerIDsSubstring[IntOffset];
   integerList[index].m_MessageType = (int)IntegerIDsSubstring[IntOffset + 1];
   integerList[index].m_ClassID = (int)IntegerIDsSubstring[IntOffset + 2];
   integerList[index].m_CategoryID = (int)IntegerIDsSubstring[IntOffset + 3];
   integerList[index].m_MessageText = MessageTextSubstring;
}

Проблема здесь: я пытаюсь распечатать все элементы в моем списке, используя цикл for:

for (int cnt3 = 0 ; cnt3 <= integerList.FindLastIndex ; cnt3++) //<----PROBLEM HERE
{
   Console.WriteLine("{0}\t{1}\t{2}\t{3}\t{4}\n", integerList[cnt3].m_MessageID,integerList[cnt3].m_MessageType,integerList[cnt3].m_ClassID,integerList[cnt3].m_CategoryID, integerList[cnt3].m_MessageText);
}

Я хочу найти последний элемент, чтобы приравнивать cnt3 в цикле for и распечатывать все записи в List. Каждый элемент в списке является объектом класса AllIntegerID, как указано выше в примере кода. Как найти последнюю действительную запись в списке?

Должен ли я использовать что-то вроде integerList.Find(integerList []. m_MessageText == null;

Если я использую это, ему понадобится индекс, который будет варьироваться от 0 до любого максимального. Значит, мне придется использовать другой цикл, который я не намерен использовать. Есть ли более короткий/лучший способ?

Спасибо, Viren

Ответ 1

Если вы просто хотите получить доступ к последнему элементу в списке, вы можете сделать

var item = integerList[integerList.Count - 1];

чтобы получить общее количество элементов в списке, вы можете использовать свойство Count

var itemCount = integerList.Count;

Ответ 2

Чтобы получить последний элемент коллекции, используйте LastOrDefault() и Последние() методы расширения

var lastItem = integerList.LastOrDefault();

ИЛИ

var lastItem = integerList.Last();

Вспомните, чтобы добавить using System.Linq;, или этот метод не будет доступен.

Ответ 3

Позволяет получить в корне вопроса вопрос, как безопасно обращаться к последнему элементу списка...

Полагая

List<string> myList = new List<string>();

Тогда

//NOT safe on an empty list!
string myString = myList[myList.Count -1];

//equivalent to the above line when Count is 0, bad index
string otherString = myList[-1];

"count-1" - это плохая привычка, если вы не гарантируете, что список не пуст.

Не существует удобного способа проверки пустого списка, кроме как сделать это.

Самый короткий способ, о котором я могу думать, -

string myString = (myList.Count != 0) ? myList [ myList.Count-1 ] : "";

вы можете изо всех сил и сделать делегат, который всегда возвращает true, и передать его в FindLast, который вернет последнее значение (или по умолчанию сконструировано valye, если список пуст). Эта функция начинается в конце списка, так что будет Big O (1) или постоянное время, несмотря на то, что метод обычно равен O (n).

//somewhere in your codebase, a strange delegate is defined
private static bool alwaysTrue(string in)
{
    return true;
}

//Wherever you are working with the list
string myString = myList.FindLast(alwaysTrue);

Метод FindLast является уродливым, если вы считаете часть делегата, но его нужно только объявить в одном месте. Если список пуст, он вернет построенное по умолчанию значение типа списка "" для строки. Принять делегата alwaysTrue еще один шаг, сделав его шаблоном вместо строкового типа, было бы более полезным.

Ответ 4

Изменить

for (int cnt3 = 0 ; cnt3 <= integerList.FindLastIndex ; cnt3++)

к

for (int cnt3 = 0 ; cnt3 < integerList.Count; cnt3++)

Ответ 5

Попробуйте использовать параметр "Для каждого" вместо списков "For". Это будет намного проще.

Ответ 6

int lastInt = integerList[integerList.Count-1];

Ответ 7

Почему бы просто не использовать свойство Count в списке?

for(int cnt3 = 0; cnt3 < integerList.Count; cnt3++)

Ответ 8

Используйте свойство Count. Последний индекс будет Count - 1.

for (int cnt3 = 0 ; cnt3 < integerList.Count; cnt3++)

Ответ 9

Вы можете найти его, сначала посчитав количество элементов в списке, например,

int count = list.Count();

Затем вы можете проиндексировать счетчик - 1, чтобы получить последний элемент в списке, например,

int lastNumber = list[count - 1];

Ответ 10

Я бы согласился, что foreach будет намного проще, чем

foreach(AllIntegerIDs allIntegerIDs in integerList)
{
Console.WriteLine("{0}\t{1}\t{2}\t{3}\t{4}\n", allIntegerIDs.m_MessageID,
allIntegerIDs.m_MessageType,
allIntegerIDs.m_ClassID,
allIntegerIDs.m_CategoryID,
allIntegerIDs.m_MessageText);
}

Также я предлагаю вам добавлять свойства для доступа к вашей информации вместо общедоступных полей, в зависимости от вашей версии .net вы можете добавить ее как public int MessageType {get; set;} и избавиться от m_ от ваших общедоступных полей, свойств и т.д. не должно быть там.

Ответ 11

Независимо от вашего первоначального вопроса, вы получите более высокую производительность, если вы будете захватывать ссылки на локальные переменные, а не индексировать в свой список несколько раз:

AllIntegerIDs ids = new AllIntegerIDs();
ids.m_MessageID = (int)IntegerIDsSubstring[IntOffset];
ids.m_MessageType = (int)IntegerIDsSubstring[IntOffset + 1];
ids.m_ClassID = (int)IntegerIDsSubstring[IntOffset + 2];
ids.m_CategoryID = (int)IntegerIDsSubstring[IntOffset + 3];
ids.m_MessageText = MessageTextSubstring;
integerList.Add(ids);

И в вашем цикле for:

for (int cnt3 = 0 ; cnt3 < integerList.Count ; cnt3++) //<----PROBLEM HERE
{
   AllIntegerIDs ids = integerList[cnt3];
   Console.WriteLine("{0}\t{1}\t{2}\t{3}\t{4}\n",
      ids.m_MessageID,ids.m_MessageType,ids.m_ClassID,ids.m_CategoryID, ids.m_MessageText);
}

Ответ 12

Я думаю, что это помогает вам. Пожалуйста, проверьте

    TaxRangers[TaxRangers.Count]. max