C#初学者控制台应用代码评审及改进建议请求
C#控制台应用代码评审与改进建议
我近期开发了一个WinForms应用,现在完成了一个控制台应用任务以完善相关功能。正在学习C#但不知从何入手,已经完成了几个任务但不确定自己是否有所进步,附上任务要求、代码,请求评审并给出改进建议。
任务要求
- 读取
kolcsonzesek.txt文件中的数据。 - 将数据存储在合适的数据结构中。
- 在控制台打印文件中记录的借阅次数。
- 计算并显示平均借阅时长(四舍五入为整数)。
- 打印最长的借阅记录(姓名+书籍标题+天数)。
- 统计持续至少14天的借阅次数。
- 检查是否存在持续恰好5天的借阅记录。
- 生成已借阅书籍的统计信息。
- 将持续至少14天的借阅记录写入
hosszu.txt文件。
现有代码
Program.cs
namespace Kolcsonzesek { internal class Program { static void Main(string[] args) { string[]rows = File.ReadAllLines("kolcsonzesek.txt"); List<Book> borrowings = new List<Book>(); foreach (string row in rows.Skip(1)) { borrowings.Add(new Book(row)); } int counted = borrowings.Count; Console.WriteLine($"3. feladat: {counted} kölcsönzés volt."); double avgtime = borrowings.Average(x => x.Days); Console.WriteLine($"4. feladat: Atlag {avgtime:F1} nap."); string longest = borrowings.OrderByDescending(x => x.Days).First().Name; Console.WriteLine($"5. feladat: {longest} volt a leghosszabb kölcsönző."); int longtime = 0; int shorttime = 0; foreach (var book in borrowings) { if (book.Days > 14) { longtime++; } if (book.Days < 5) { shorttime++; } else { Console.WriteLine($"7. feladat: Nincs 5 napnál rövidebb kölcsönzés."); } } Console.WriteLine($"6. feladat: {longtime} 14napnal tobbig tarto kölcsönzés volt."); Console.WriteLine($"7. feladat: {shorttime} 14napnal tobbig tarto kölcsönzés volt."); Dictionary<string, int> stats = new Dictionary<string, int>(); foreach (var book in borrowings) { if (stats.ContainsKey(book.Title)) { stats[book.Title]++; } else { stats.Add(book.Title, 1); } } Console.WriteLine("8. feladat: Kölcsönzési statisztika:"); foreach (var s in stats) { Console.WriteLine($"{s.Key} - {s.Value} db"); } List<string> output = new List<string>(); output.Add("Nev;Cim;Napok"); foreach (var book in borrowings) { if (book.Days >= 14) { output.Add($"{book.Name};{book.Title};{book.Days}"); } } File.WriteAllLines("hosszu.txt", output); } } }
Book.cs
using System; using System.Collections.Generic; using System.Data; using System.Text; namespace Kolcsonzesek { public class Book { public string Name { get; set;} public string Title { get; set;} public int Days { get; set;} public Book(string row) { string[] s=row.Split(';'); Name = s[0]; Title = s[1]; Days = int.Parse(s[2]); } } }
代码问题与改进建议
当前代码能完成部分任务,但存在功能错误和可优化点,需要修改,具体如下:
一、功能错误修正
任务4不符合要求:要求平均借阅时长四舍五入为整数,但现有代码用
avgtime:F1保留一位小数。- 改进:用
Math.Round(avgtime)取整,输出改为$"4. feladat: Átlag {Math.Round(avgtime)} nap."
- 改进:用
任务5信息缺失:要求打印最长借阅记录的「姓名+书籍标题+天数」,但现有代码只输出了姓名。
- 改进:先获取完整的最长记录对象,再拼接所有信息:
var longestBorrow = borrowings.OrderByDescending(x => x.Days).First(); Console.WriteLine($"5. feladat: {longestBorrow.Name} - {longestBorrow.Title} ({longestBorrow.Days} nap) volt a leghosszabb kölcsönzés.");
- 改进:先获取完整的最长记录对象,再拼接所有信息:
任务7完全错误:要求检查是否存在恰好5天的借阅记录,但现有代码逻辑是统计
<5天的数量,还在循环中多次输出无关信息,最后输出描述也写错成「14天以上」。- 改进:用LINQ直接判断是否存在,输出正确结果:
bool hasExact5Days = borrowings.Any(b => b.Days == 5); Console.WriteLine($"7. feladat: {(hasExact5Days ? "Van" : "Nincs")} pontosan 5 napos kölcsönzés."); - 同时删除原代码中循环里的
else分支输出,以及最后错误的7. feladat输出行。
- 改进:用LINQ直接判断是否存在,输出正确结果:
任务6统计逻辑偏差:要求统计「至少14天」(即
>=14),但现有代码判断的是>14,会漏掉刚好14天的记录。- 改进:将判断条件改为
book.Days >= 14
- 改进:将判断条件改为
二、代码优化建议
添加异常处理:当前代码未处理文件不存在、数据格式错误(比如
int.Parse失败)等异常,运行时可能崩溃。- 示例:给文件读取和数据解析部分加
try-catch:try { string[] rows = File.ReadAllLines("kolcsonzesek.txt"); // ... 后续解析逻辑 } catch (FileNotFoundException) { Console.WriteLine("Hiba: kolcsonzesek.txt fájl nem található!"); } catch (FormatException ex) { Console.WriteLine($"Hiba: Érvénytelen adatformátum - {ex.Message}"); }
- 示例:给文件读取和数据解析部分加
简化统计逻辑:用LINQ替代手动循环统计,代码更简洁可读:
- 统计至少14天的借阅次数:
int longTermCount = borrowings.Count(b => b.Days >= 14); - 书籍借阅统计可以用
GroupBy:var bookStats = borrowings.GroupBy(b => b.Title) .Select(g => new { Title = g.Key, Count = g.Count() });
- 统计至少14天的借阅次数:
优化Book类设计:
- 属性改为只读(
init或私有set),避免实例化后被意外修改:public string Name { get; init; } public string Title { get; init; } public int Days { get; init; } - 删除Book类中无用的引用(
using System.Data;、using System.Collections.Generic;等) - 数据解析时添加边界检查,避免数组越界:比如判断
s.Length ==3再进行赋值和解析。
- 属性改为只读(
变量命名规范:使用更清晰的变量名,比如
avgtime改为averageDays,longtime改为longTermBorrowCount,提升代码可读性。减少集合遍历次数:当前代码多次遍历
borrowings集合(统计、排序、生成文件等),可以在一次遍历中完成多个统计,提升性能(数据量大时更明显)。
三、修改后代码示例(核心部分)
static void Main(string[] args) { try { string[] rows = File.ReadAllLines("kolcsonzesek.txt"); List<Book> borrowings = rows.Skip(1) .Select(row => new Book(row)) .ToList(); // 任务3 Console.WriteLine($"3. feladat: {borrowings.Count} kölcsönzés volt."); // 任务4 double averageDays = borrowings.Average(x => x.Days); Console.WriteLine($"4. feladat: Átlag {Math.Round(averageDays)} nap."); // 任务5 var longestBorrow = borrowings.OrderByDescending(x => x.Days).First(); Console.WriteLine($"5. feladat: {longestBorrow.Name} - {longestBorrow.Title} ({longestBorrow.Days} nap) volt a leghosszabb kölcsönzés."); // 任务6 int longTermCount = borrowings.Count(b => b.Days >= 14); Console.WriteLine($"6. feladat: {longTermCount} 14 napnál többig tartó kölcsönzés volt."); // 任务7 bool hasExact5Days = borrowings.Any(b => b.Days == 5); Console.WriteLine($"7. feladat: {(hasExact5Days ? "Van" : "Nincs")} pontosan 5 napos kölcsönzés."); // 任务8 Console.WriteLine("8. feladat: Kölcsönzési statisztika:"); var bookStats = borrowings.GroupBy(b => b.Title) .Select(g => new { Title = g.Key, Count = g.Count() }); foreach (var stat in bookStats) { Console.WriteLine($"{stat.Title} - {stat.Count} db"); } // 任务9 var longTermRecords = borrowings.Where(b => b.Days >= 14) .Select(b => $"{b.Name};{b.Title};{b.Days}") .Prepend("Nev;Cim;Napok"); File.WriteAllLines("hosszu.txt", longTermRecords); } catch (Exception ex) { Console.WriteLine($"Hiba történt: {ex.Message}"); } }
内容的提问来源于stack exchange,提问作者user32746036
相关产品推荐
相关产品推荐

