之前在给一个工厂客户开发一套"售后包装防错系统"的时候,由于业务比较复杂,
每个表的字段基本都保持在10-20个字段区间,如下截图(可向右滑动滚动条)
正常的做法,肯定是一顿卡卡操作,新建列,编辑列,一个一个的去写 name,DataPropertyName, HeaderText....
字段少的时候,我也比较喜欢这种方式,无脑开发最爽了。但是转念一想,老子的时间很宝贵啊,家里娃还在床上哭呢,我得去抱娃。
有没有更快速,便捷的方法呢?要不说人类进步的一大原因就是人懒呢,能做一步,绝不做两步。
好了,废话不多说,直接先说思路,再上代码,大佬嘛,就请要么走开,要么嘴下留情。
文中展示的代码,目的只是为了显示这么一个思路逻辑,至于优美不优美,牛逼不牛逼啥的,咱也就不要太计较了。
我们先解决下面这些问题:
1:这个类对象中的字段属性能不能不要我一个一个的去写
2:sql语句中的queryColumn能不能不要我一个一个去写
3:这datagridview列能不能动态添加,我也不想去写
你瞅瞅,你这要求这么多,还不值得点上一根烟,好好的思考下为什么吗?
好了,我们一个问题一个问题的解决和上代码
1:这个类对象的字段属性值,可以通过
select column_name from INFORMATION_SCHEMA.COLUMNs
where table_name='P_BMWDetailBom'
去查询数据库,找到表中的字段集合,我这里没有做这样的操作,诸君请自行脑补。
2:结合第二,第三个问题,我在类对象里 加了一个自定义特性 ,来标记 某个属性是否需要拼接到sql中,是否需要显示在datagridview列中,并且显示的HeaderText 是啥,然后再通过反射,获取到对应的属性和特性,由此动态的去获取数据库列,拼接sql,添加datagridview列。
一:自定义特性
cs
public class ChangeShow : Attribute
{
/// <summary>
/// 是否需要查询
/// 显示
/// </summary>
public bool Value { get; private set; }
/// <summary>
/// 显示的text
/// </summary>
public string TextStr { get; private set; }
public ChangeShow(bool value,string textStr)
{
Value = value;
TextStr = textStr;
}
}
二:类对象属性上标记特性
cs
[Serializable]
public class P_BMWDetailBom
{
public int Id { get; set; }
[ChangeShow(true, "长城零件号")]
public string GWMPartCode { get; set; }
[ChangeShow(true, "BMW11位零件号")]
public string BWMPartCode11Bit { get; set; }
[ChangeShow(true, "中文零件描述")]
public string PartCodeName { get; set; }
三:Form界面 绑定datagridview集合
cs
private void Test_Load(object sender, EventArgs e)
{
///待查询的queryColumns列集合
List<string> queryColumns = new List<string>();
// 获取类的属性描述
// 获取类型信息
Type type = typeof(P_BMWDetailBom);
// 遍历所有属性
foreach (var property in type.GetProperties())
{
// 获取属性上的自定义Attribute
var attributes = property.GetCustomAttributes(typeof(ChangeShow), true);
foreach (ChangeShow attribute in attributes)
{
if (attribute.Value) {
queryColumns.Add(property.Name);
// 创建新列
DataGridViewColumn newColumn = new DataGridViewTextBoxColumn();
// 设置新列的属性
newColumn.HeaderText = attribute.TextStr;
newColumn.Name = property.Name;
// 根据需要设置其他属性,例如 newColumn.ValueType = typeof(int);
newColumn.DataPropertyName = property.Name;
// 将新列添加到DataGridView中
dataGridView1.Columns.Add(newColumn);
}
}
}
//查询数据库
BMWDetailBomBll bll = new BMWDetailBomBll();
DataTable dt = bll.pageData(queryColumns, pageIndex, pageSize);
this.dataGridView1.DataSource = dt;
string dddd = "";
}
四:Dal层 查询语句拼接,各位可以根据自己的需要,自行按照个人喜好处理
cs
public DataTable pageData(List<string> queryColumns, int pageIndex, int pageSize)
{
if (queryColumns != null && queryColumns.Count > 0)
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.Append("select ");
foreach (string key in queryColumns)
{
stringBuilder.Append("a.");
stringBuilder.Append(key);
stringBuilder.Append(",");
}
string querySql = stringBuilder.ToString().TrimEnd(',');
stringBuilder.Clear();
stringBuilder.Append(querySql);
stringBuilder.Append(" from (select Row_number() over(order by id desc) as rownum,* from P_BMWDetailBom where 1=1 ) a where a.rownum between ");
stringBuilder.Append(((pageIndex - 1) * pageSize + 1));
stringBuilder.Append(" and ");
stringBuilder.Append(pageSize * pageIndex);
DataSet ds = SqlUtil.ExecuteQuery(stringBuilder.ToString(), null);
return ds.Tables[0];
}
else
return null;
}
最终测试结果