在循环浏览ListView控件时将特定子项写入.txt?

时间:2013-11-15 22:43:36

标签: c# winforms listview foreach listviewitem

我的下面的代码首先将一个感叹号(!)分隔的标题写入.txt文件,然后遍历ListView控件中的每个项目和subItem,将每个记录值放在我的.txt文件中的新行上。在ListBox中用户查看时需要所有值,但在写入文件时,我只需要编写下一步中使用的字段,使用.txt文件作为MS Word MailMerge文档的数据源。

我需要一种方法来获取ListView列标题所在的值,而不是循环并将每个记录字段值附加到我的StringBuilder:

memno 名称 地址1 地址2 地址3 萨尔 fuldate SYS

private void btnMerge_Click(object sender, EventArgs e)
        {
            try
            {    
                string docLoc = "";
                string docSource = "";
                StringBuilder sb;
                // Change this to the DataSource FilePath
                StreamWriter sw = new StreamWriter("C:\\Users\\NAME\\Desktop\\Test2.txt");
                string fileHeaderTxt = "memno!name!address1!address2!city!state!zip!old_addr1!old_addr2!old_city!old_state!old_zip!sys!fuldate!sex!lname!sal!address3";
                sb = new StringBuilder();
                sb.Append(fileHeaderTxt);
                sw.WriteLine(sb.ToString());
                sb.Clear();

                if (lvData.Items.Count > 0)
                {
                    foreach (ListViewItem lvI in lvData.Items)
                    {
                        sb = new StringBuilder();
                        foreach (ListViewItem.ListViewSubItem lvSI in lvI.SubItems)
                        {
                            sb.Append(string.Format("{0}!", lvSI.Text));
                        }
                        sw.WriteLine(sb.ToString());
                    }
                    sw.WriteLine();
                }
                //sb.Clear();
                sw.Close();
                MessageBox.Show("Complete");

                if (rbPrint.Checked)
                {
                    Print(docLoc, docSource);
                }
                if (rbCommit.Checked)
                {
                    Commit_NetFYI();
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show("Source:\t" + ex.Source + "\nMessage: \t" + ex.Message + "\nData:\t" + ex.Data);
            }
            finally
            {
                //
            }
        }

我在过去的几个小时里一直在抨击这件事,似乎无法得到它。有人有想法吗?

修改

我使用Grammarian的解决方案修改了我的代码,但似乎我遗漏了一些东西。每次循环迭代都会写入一行,其中包含所有先前的循环值以及新值。

粗略示例:

头1!头2!Header3!Header4

1!2!3!4

1!2!3!4!5!6!7!8

1!2!3!4!5!6!7!8!9!10!11!12

1!2!3!4!5!6!7!8!9!10!11!12!13!14!15!16 等

这是我目前的代码:

private void btnMerge_Click(object sender, EventArgs e)
        {
            try
            {
                string docLoc = "";
                string docSource = "";
                StringBuilder sb;
                // Change this to the DataSource FilePath
                StreamWriter sw = new StreamWriter("C:\\Users\\NAME\\Desktop\\Test2.txt");
                string fileHeaderTxt = "memno!name!address1!address2!city!state!zip!old_addr1!old_addr2!old_city!old_state!old_zip!sys!fuldate!sex!lname!sal!address3";
                sb = new StringBuilder();
                sb.Append(fileHeaderTxt);
                sw.WriteLine(sb.ToString());
                sb.Clear();

                if (lvData.Items.Count > 0)
                {
                    foreach (ListViewItem lvI in lvData.Items)
                    {
                        var indices = new int[] { 0, 1, 2, 3, 12, 13, 16, 17 };
                        foreach (int i in indices)
                        {
                              sb.Append(string.Format("{0}!", lvI.SubItems[i].Text));
                        }
                        sw.WriteLine(sb.ToString());
                        sb.Clear();
                    }
                    sw.WriteLine();
                }
          }
    }

EDIT2

知道了,每次通过我的第一个循环后都没有清除我的stringBuilder对象。编辑上面的代码以反映工作代码。

1 个答案:

答案 0 :(得分:1)

不是总是只迭代所有子项,而是按照你想要的顺序创建一个子项索引数组,并迭代索引。

var indices = new [] { 0, 1, 2, 4, 9 }; // whatever you want
foreach (int i in indices)
{
    sb.Append(string.Format("{0}!", lvI.SubItems[i].Text));
}
相关问题