C#读入txt文本文件时,因为文件行数比较的多,我想制作进度条,可文件流中没有行数属性,求怎么解决!!!
展开全部
进度条是这样实现的 :
------------------------------------------------------------------------------------------------------------------
首先,你可以获取到整个文件的大小。
然后,你自己定义一个缓冲区(说白了就是一个字节数组Byte[]),这缓冲区的大小由你来定
1024就是1kb。5kb:5120。自己看着办。
而根据文件总大小/缓冲区大小,就可以确定总共要进行多少次缓冲区的缓冲才能交换完成。
具体段数计算是这样的:
int x=总文件大小/缓冲区大小;
if(总文件大小%缓冲区大小>0)
x++;
这段代码你应该是要看得懂的,我就不解释了。
然后,在进度条的属性不是有个每次走多少个百分比吗?
100/段数 就是那个数了。
-------------------------------------------------------------------------
同时,在进行数据的传输过程中,一般不能够使用主线程进行复制
这样有时候会使得程序卡在那里不同。所以一般是使用子线程进行操作。
在这里我就不对线程的知识进行赘述。
以下是数据复制过程的代码:
private void copyfile()
{
Stream sr = File.OpenRead(this.textBox1.Text);
Stream sw = File.OpenWrite(this.textBox2.Text);
BufferedStream bin = new BufferedStream(sr);
BufferedStream bout = new BufferedStream(sw);
int bytecount = 5120;
byte[] bs = new byte[bytecount];
int count;
long psmax = sr.Length / (long)bytecount;
if (sr.Length % bytecount != 0)
psmax++;
int pscur = 0;
while ((count = bin.Read(bs, 0, bytecount)) > 0)
{
bout.Write(bs, 0, count);
bout.Flush();
pscur++;
SetText(pscur, psmax);
}
bin.Close();
bout.Close();
sr.Close();
sw.Close();
MessageBox.Show("复制完成!");
th.Abort();
}
delegate void SetTextCallback(int text,long max);
private void SetText(int text,long max)
{
if (this.progressBar1.InvokeRequired)
{
SetTextCallback d = new SetTextCallback(SetText);
this.Invoke(d, new object[] { text,max });
}
else
{
this.progressBar1.Maximum = (int)max;
this.progressBar1.Value = text;
}
}
其中 SetText()是直接从MSDN中复制粘贴的一段关于线程安全的函数。有兴趣可以查看MSDN文档。
根据这个原理,请自行修改部分语句实现数据读取功能。
------------------------------------------------------------------------------------------------------------------
首先,你可以获取到整个文件的大小。
然后,你自己定义一个缓冲区(说白了就是一个字节数组Byte[]),这缓冲区的大小由你来定
1024就是1kb。5kb:5120。自己看着办。
而根据文件总大小/缓冲区大小,就可以确定总共要进行多少次缓冲区的缓冲才能交换完成。
具体段数计算是这样的:
int x=总文件大小/缓冲区大小;
if(总文件大小%缓冲区大小>0)
x++;
这段代码你应该是要看得懂的,我就不解释了。
然后,在进度条的属性不是有个每次走多少个百分比吗?
100/段数 就是那个数了。
-------------------------------------------------------------------------
同时,在进行数据的传输过程中,一般不能够使用主线程进行复制
这样有时候会使得程序卡在那里不同。所以一般是使用子线程进行操作。
在这里我就不对线程的知识进行赘述。
以下是数据复制过程的代码:
private void copyfile()
{
Stream sr = File.OpenRead(this.textBox1.Text);
Stream sw = File.OpenWrite(this.textBox2.Text);
BufferedStream bin = new BufferedStream(sr);
BufferedStream bout = new BufferedStream(sw);
int bytecount = 5120;
byte[] bs = new byte[bytecount];
int count;
long psmax = sr.Length / (long)bytecount;
if (sr.Length % bytecount != 0)
psmax++;
int pscur = 0;
while ((count = bin.Read(bs, 0, bytecount)) > 0)
{
bout.Write(bs, 0, count);
bout.Flush();
pscur++;
SetText(pscur, psmax);
}
bin.Close();
bout.Close();
sr.Close();
sw.Close();
MessageBox.Show("复制完成!");
th.Abort();
}
delegate void SetTextCallback(int text,long max);
private void SetText(int text,long max)
{
if (this.progressBar1.InvokeRequired)
{
SetTextCallback d = new SetTextCallback(SetText);
this.Invoke(d, new object[] { text,max });
}
else
{
this.progressBar1.Maximum = (int)max;
this.progressBar1.Value = text;
}
}
其中 SetText()是直接从MSDN中复制粘贴的一段关于线程安全的函数。有兴趣可以查看MSDN文档。
根据这个原理,请自行修改部分语句实现数据读取功能。
展开全部
先要得到行,然后以当前行的位置为进度。
读行,这个可以参考一下:
StreamReader srStream = new StreamReader(filePath, Encoding.GetEncoding("GB2312"));//实现一个 TextReader,使其以GB2312编码从字节流中读取字符。
dgv.Columns.Clear();
String sLine = srStream.ReadLine();
string[] starry = sLine.ToString().Split(new string[] { " ", "\t" }, StringSplitOptions.RemoveEmptyEntries);
while (!srStream.EndOfStream)
{
for (int i = 0; i < starry.Length-1; i++)
{
dgv[0, 0].Value = starry[i].ToString();
}
}
srStream.Close();
读行,这个可以参考一下:
StreamReader srStream = new StreamReader(filePath, Encoding.GetEncoding("GB2312"));//实现一个 TextReader,使其以GB2312编码从字节流中读取字符。
dgv.Columns.Clear();
String sLine = srStream.ReadLine();
string[] starry = sLine.ToString().Split(new string[] { " ", "\t" }, StringSplitOptions.RemoveEmptyEntries);
while (!srStream.EndOfStream)
{
for (int i = 0; i < starry.Length-1; i++)
{
dgv[0, 0].Value = starry[i].ToString();
}
}
srStream.Close();
追问
我是想在执行类似你上边写的程序的同时加上一个进度条的功能,能具体点说进度条吗?
追答
参考这个:
SqlDataAdapter myDa = new SqlDataAdapter("select rtrim(A.KNO) as 客户编号,rtrim(A.NA) as 姓名,rtrim(A.BKNO) as 身份证号码,rtrim(A.BKHO) 开户银行,rtrim(A.Tel) as 联系电话,rtrim(B.NA) as 地址 from TempNHDIR as A inner join tempxzqh B on left(A.KNO,5)=B.DM where Len(A.KNO)=8", myCon);
DataSet myDs = new DataSet();
myDa.Fill(myDs);
int count = myDs.Tables[0].Rows.Count;
labprogressBar.Visible = true;
labprogressBar.Visible = true;
labprogressBar.Minimum = 0;
labprogressBar.Maximum = 100;
labprogressBar.BackColor = Color.Green;
labprogressBar.Step = 100;
for (int i = 0; i < count; i++)
{
labprogressBar.Value = (i + 1) * 100 / count;
labprogressBar.Text = (labprogressBar.Value * 100 / labprogressBar.Maximum).ToString() + "%";//显示百分比
}
dGV.DataSource = myDs.Tables[0];
labprogressBar.Visible = false;
labprogressBar.Visible = false;
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
有的
既然可以一行一行读
肯定有标识 是表示 行的
读那个标识 计算有多少个
然后从都一行一行读 进度条显示
既然可以一行一行读
肯定有标识 是表示 行的
读那个标识 计算有多少个
然后从都一行一行读 进度条显示
追问
好像是没有标识,我找了一天了都没翻到
追答
把文件指针移到最后
有这个函数吗?
类似 SeekToEnd
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
考虑两种方法:
1.在 txt 中记录行数(推荐这个)。
2.换行的话是有特殊的字符来实现的(\n),可以获取换行符出现的次数。
1.在 txt 中记录行数(推荐这个)。
2.换行的话是有特殊的字符来实现的(\n),可以获取换行符出现的次数。
追问
你的意思是在第一行加上行总数,或者是在每一行都加行号吗?
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询