Berikut ini adalah ekstrak dari kode saya:
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;
}
Saya mencoba menggunakan yang berikut ini dalam kode fungsi utama () saya:
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;
}
Masalahnya ada di sini: Saya mencoba untuk mencetak semua elemen dalam Daftar saya menggunakan for 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);
}
Saya ingin menemukan elemen terakhir sehingga saya menyamakan cnt3 di loop untuk saya dan mencetak semua entri dalam Daftar. Setiap elemen dalam daftar adalah objek dari kelas AllIntegerIDs sebagaimana disebutkan di atas dalam contoh kode. Bagaimana cara menemukan entri terakhir yang valid dalam Daftar?
Haruskah saya menggunakan sesuatu seperti integerList.Find (integerList []. M_MessageText == null;
Jika saya menggunakan itu akan memerlukan indeks yang akan berkisar dari 0 hingga apa pun maksimum. Berarti saya harus menggunakan yang lain untuk loop yang tidak ingin saya gunakan. Apakah ada cara yang lebih pendek / lebih baik?
Terima kasih, Viren
AllIntegerIDs newItem = new AllIntegerID();
, gunakan itu untuk menetapkan semua bidang lalu panggilintegerList.Add(newItem)
. Atau gunakan properti daripada bidang dan gunakan sintaks penginisialisasi objek C # 3.0.Jawaban:
Jika Anda hanya ingin mengakses item terakhir dalam daftar yang dapat Anda lakukan
untuk mendapatkan jumlah total item dalam daftar, Anda dapat menggunakan properti Count
sumber
Last
/LastOrDefault
seperti yang disebutkan di bawah ini.Enumerable.Last
akan mengeluarkan pengecualian jika daftar kosong. Jika Anda memanggilEnumerable.LastOrDefault
dan melewati daftar tipe nilai, nilai default akan dikembalikan jika daftar kosong. Jadi, jika Anda mendapatkan kembali 0 dariList<int>
Anda tidak akan tahu apakah daftar itu kosong atau nilai terakhir adalah 0. Singkatnya, Anda perlu memeriksaCount
mekanisme pengambilan mana yang Anda pilih untuk digunakan.var element = list[list.Count - 1]
sangat singkat dan mudah dibaca. Tidak perlu menggunakan metode ekstensiUntuk mendapatkan item terakhir dari koleksi, gunakan metode ekstensi LastOrDefault () dan Last ()
ATAU
Ingat untuk menambahkan
using System.Linq;
, atau metode ini tidak akan tersedia.sumber
First
,FirstOrDefault
,Last
,LastOrDefault
,Single
,SingleOrDefault
,ElementAt
danElementAtOrDefault
dioptimalkan untukIList<TSource>
,Count
danContains
dioptimalkan untukICollection<TSource>
danCast<TResult>
dioptimalkan untukIEnumerable<TResult>
.using System.Linq;
System.Linq.Enumerable
tidak benar-benar 'dioptimalkan'. Inilah kode untukEnumerable.Last
metode ini.System.Linq.Enumerable.Last
, saya setuju dengan 0b101010 -Last()
kode ini tidak "dioptimalkan untukList<>
s" -Last()
hanya pembungkus yang jelek, yang secara default adalahreturn list[list.Count-1]
seandainya argumennya adalahIList
, dan beralih ke daftar sampai akhir dalam kasus itu bukan ... menjadikannya solusi yang sangat buruk jikaIList
aLinkedList
, karena pengindeks hanya akan pergi melalui seluruh daftar sia-sia (saya belum menemukan override iterasi mundurItem[]
dengan indeks> Hitung / 2 di c # sources, YMMV )Mari kita dapatkan akar dari pertanyaan, bagaimana cara mengatasi elemen terakhir Daftar dengan aman ...
Asumsi
Kemudian
"count-1" adalah kebiasaan buruk kecuali Anda menjamin bahwa daftar tersebut tidak kosong.
Tidak ada cara mudah untuk memeriksa daftar kosong kecuali melakukannya.
Cara terpendek yang bisa saya pikirkan adalah
Anda bisa keluar semua dan membuat delegasi yang selalu mengembalikan true, dan meneruskannya ke FindLast, yang akan mengembalikan nilai terakhir (atau default dibangun valye jika daftar kosong). Fungsi ini dimulai pada akhir daftar sehingga akan menjadi Big O (1) atau waktu konstan, meskipun metode biasanya O (n).
Metode FindLast jelek jika Anda menghitung bagian delegasi, tetapi hanya perlu dinyatakan satu tempat. Jika daftar kosong, itu akan mengembalikan nilai dibangun standar dari tipe daftar "" untuk string. Mengambil delegasi alwaysTrue selangkah lebih jauh, menjadikannya templat daripada tipe string, akan lebih bermanfaat.
sumber
myList.FindLast(_unused_variable_name => true);
Ini akan berfungsi terlepas dari jenisnya. Versi yang lebih pendekmyList.FindLast(_ => true);
, tetapi saya menemukan garis bawah (atau pengenal karakter tunggal lainnya) dapat sedikit membingungkan di kali.sumber
Perubahan
untuk
sumber
Gunakan
Count
properti. Indeks terakhir adalahCount - 1
.sumber
Anda dapat menemukannya dengan terlebih dahulu menghitung jumlah elemen dalam daftar misalnya
Kemudian Anda dapat mengindeks hitungan - 1 untuk mendapatkan elemen terakhir dalam daftar misalnya
sumber
Di C # 8.0 Anda bisa mendapatkan item terakhir dengan ^ penjelasan lengkap operator
sumber
Mengapa tidak menggunakan properti Count di Daftar?
sumber
Terlepas dari pertanyaan awal Anda, Anda akan mendapatkan kinerja yang lebih baik jika Anda menangkap referensi ke variabel lokal daripada mengindeks ke daftar Anda beberapa kali:
Dan di
for
loop Anda :sumber
Saya harus setuju bahwa foreach akan jauh lebih mudah
Saya juga menyarankan Anda menambahkan properti untuk mengakses informasi Anda alih-alih bidang publik, tergantung pada versi .net Anda, Anda dapat menambahkannya
public int MessageType {get; set;}
dan menyingkirkannya darim_
bidang publik Anda, properti dll karena tidak seharusnya ada di sana.sumber
Saya pikir ini membantu Anda. Silakan periksa
sumber