如何在 SqlDataReader 之前知道或获取数组大小?并将其作为 json 返回
Posted
技术标签:
【中文标题】如何在 SqlDataReader 之前知道或获取数组大小?并将其作为 json 返回【英文标题】:How can I know or get the Array Size before a SqlDataReader? and return it as a json 【发布时间】:2014-09-05 19:19:25 【问题描述】:我想知道我的数组的大小以循环所需的时间,但我不知道如何以有效的方式进行,我能想到的唯一方法是将其放入阅读器并计数,然后使用另一个时间阅读器并插入值:(我是学生
这里是代码
myConnection.Open();
SqlCommand sqlCommand = new SqlCommand(" SELECT * FROM table ", myConnection);
SqlDataReader dr = sqlCommand.ExecuteReader();
Calendar[] loArrayRegistrosCalendario = new Calendar[200]; //200 As an example
if (dr != null)
int i = 0;
while (dr.Read())
Calendar loRegistroDia = new Calendar();
loRegistroDia.User = (dr["user"].ToString());
loArrayRegistrosCalendario[i] = loRegistroDia;
i = i + 1;
return loArrayRegistrosCalendario;
【问题讨论】:
为什么不使用支持动态项目数的类(如List<>()
),然后如果你有使用数组你可以调用.ToArray()
?
我已经用 list 做了,但我需要一个 json 对象,这就是我创建一个类的原因:C
您可以像数组一样轻松地将 List 序列化为 JSON 数组。
真的吗? D: 我已经调查了 3 个小时才知道我需要开设一个课程并这样做,因为我必须对其进行序列化:s
Here is an example where I've serialize both a list and an array, they are exactly the same。请注意,您的问题是一个不好的问题,因为它是在最近的编辑之前,XY Problem。
【参考方案1】:
你根本不需要数组。
myConnection.Open();
var loArrayRegistrosCalendario = new List<Calendar>();
using (SqlCommand sqlCommand = new SqlCommand(" SELECT * FROM table ",
myConnection);)
using (SqlDataReader dr = sqlCommand.ExecuteReader())
if (dr != null)
while (dr.Read())
Calendar loRegistroDia = new Calendar();
loRegistroDia.User = (dr["user"].ToString());
loArrayRegistrosCalendario.Add(loRegistroDia);
return loArrayRegistrosCalendario;
(附带说明,请正确处理 IDisposable 对象,例如应正确处理 SqlCommand 和 SqlDataReader。我建议对两者都使用 using()
语句。)
序列化日历数组和日历列表将产生相同的结果: DotNetFiddle Example.
public class Program
public static void Main()
var myobject = new MyObject();
myobject.Calendars1 = new List<Calendar>();
for (DateTime dt = new DateTime(1980,1,1); dt <= new DateTime(1981,1,1); dt = dt.AddMonths(1))
myobject.Calendars1.Add(new Calendar() Name = dt.ToString("MMMM") );
myobject.Calendars2 = myobject.Calendars1.ToArray();
var json1 = JsonConvert.SerializeObject(myobject.Calendars1);
var json2 = JsonConvert.SerializeObject(myobject.Calendars2);
Console.WriteLine(json1);
Console.WriteLine(json2);
public class MyObject
public List<Calendar> Calendars1 get; set;
public Calendar[] Calendars2 get; set;
public class Calendar
public string Name get; set;
结果:
["姓名":"一月","姓名":"二月","姓名":"三月","姓名":"四月","姓名":"五月","姓名":"六月","姓名":"七月","姓名":"八月","姓名":"九月","姓名":"十月","姓名":"十一月","姓名":"十二月","姓名":"一月"]
["姓名":"一月","姓名":"二月","姓名":"三月","姓名":"四月","姓名":"五月","姓名":"六月","姓名":"七月","姓名":"八月","姓名":"九月","姓名":"十月","姓名":"十一月","姓名":"十二月","姓名":"一月"]
【讨论】:
List<Calendar[200]>
数组列表?这是你真正想要的吗?
@AaronLS 绝对! :) 谢谢。
@Erik Philips 真棒、高效、完整且漂亮的答案!非常感谢:)【参考方案2】:
只需创建一个 SQL 命令来获取计数,如下所示:
SqlCommand sqlCommand = new SqlCommand(" SELECT Count (*) FROM table ", myConnection);
int rows = sqlCommand.ExecuteScalar();
Calendar[] loArrayRegistrosCalendario = new Calendar[rows];
【讨论】:
我对这里的反对票感到困惑。如果他根据数据集的大小创建他的数组,那么它肯定只会循环正确的项目数......还是我在这里遗漏了什么? 也许是因为这增加了对数据库的另一个调用。另外,如果在获取计数和选择行之间从表中添加或删除行怎么办? 我部分同意你的第一点,尽管我认为在这个例子中开销是最小的。但是,我看不到行的添加/删除是一个问题,除非它发生在打开阅读器和获取计数之间的瞬间。 根据我的经验,在一瞬间发生的事情比人们想象的要频繁得多。竞态条件可能很难追踪,最好尽可能避免产生竞态条件。以上是关于如何在 SqlDataReader 之前知道或获取数组大小?并将其作为 json 返回的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 SqlDataReader 获取位值并将其转换为布尔值?
如何从 SqlDataReader 获取 int32 和字符串。收到错误 System.IndexOutOfRangeException: 'StudentID'