关于用户体验的意见 - C# Winforms
我有一个过程需要不到 5 秒的时间才能完成。用户很可能会注意到按下“开始”按钮后程序会闪烁几秒钟。
我的问题是:
这是通常会转储到后台工作程序的东西,还是有另一种 .NET 方法来处理小任务,或者这是不应该担心的东西?
供参考: 该过程打开用户指定的 Excel 文件,处理未知数量的行(我相信由于 Excel 的原因,最多 150 万行),并查询数据库(非常快的查询)。因此,在最坏的情况下,用户上传 150 万行的 Excel 文件,并且在非常慢的互联网连接上运行。
I’ve got a process which will take a little under 5 seconds to complete. The user will most likely notice the program flicker for a few seconds after pushing the “go” button.
My question is:
Is this something that would normally be dumped onto a background worker, or is there another .NET method for handling small tasks, or is this something that shouldn’t be a concern?
FYI:
The process opens a user specified excel file, processes an unknown number of lines (max 1.5 million due to excel I believe), and queries a database (very quick query). So at the worst case scenario the user uploads a 1.5 million row excel file and is running on a very slow internet connection.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(8)
如果您不希望用户在上传文件时能够执行任何操作,则无需将其放在不同的线程上。
如果您希望用户在上传文件时能够继续执行其他任务,请将其放在不同的线程上。
作为一般经验法则,如果我遇到这样的情况,我绝对不希望用户在长时间运行的进程进行时执行任何操作,我会禁用表单上的控件,直到任务完成,并且通常使用状态指示器显示正在发生的进展。
我个人关于是否允许用户交互的指导方针是,流程的结果是否可以通过中途的用户操作进行更改。
例如,我们有一个程序将高度标准化数据库(标准化到报告缓慢的程度)上的一堆查询解析为“可报告”表,并且我不希望用户更改其中一个源表中的数据当查询运行时,因为它会给出愚蠢的结果。
如果在进程发生时允许用户交互没有坏处,则将其放入另一个线程中。
编辑
实际上,在阅读@UrbanEsc和@archer的评论后,我同意他们的观点。仍然将其放在不同的线程上并冻结控件(并在可能的情况下包括进度指示器)。
If you don't want the user to be able to do anything while the file is being uploaded, then you don't need to put it on a different thread.
If you want the user to be able to go on to other tasks while the file is uploading, put it on a different thread.
As a general rule of thumb, if I have a situation where I absolutely don't want the user to do anything while a long-running process is going, I disable the controls on the form until the task is complete, and usually use a status indicator to show that progress is happening.
My personal guideline for whether or not to allow user interaction is if the results of a process could be altered by a user action in mid-stream.
For example, one program that we have parses a bunch of queries on a highly normalized database (normalized to the point where reporting is sloooow) into "reportable" tables, and I don't want the user altering data in one of the source tables while the query is running, because it will give goofy results.
If there is no harm in allowing user interaction while the process is occuring, then put it in another thread.
Edit
Actually, on reading @UrbanEsc and @archer's comments, I agree with them. Still put it on a different thread and freeze the controls (and include a progress indicator where possible).
我会将其推送给后台工作人员。这样做将使 UI 保持响应。如果进程确实滞后超过几秒钟,用户就会开始感到紧张……尤其是当滞后进程导致 UI“冻结”时。
I would push this to a background worker. Doing so will keep the UI responsive. If the process ever does lag for more than a few seconds, users start getting nervous ...especially when the lagging process causes the UI to be 'frozen'.
从用户体验的角度来看,最好将作业交给不同的线程或异步工作人员,并告诉用户他的请求正在后台处理。一旦工作人员完成,就可以处理成功/失败消息并根据需要向用户显示。
From a user experience point of view it might be best to hand the job over to a different thread or an asynchronous worker and tell the user that his request is being processed in the background. Once the worker finishes, a success/failure message can be handled and shown to the user as required.
处理该问题最便宜的方法是在处理过程中将光标变成沙漏。这告诉用户请稍候,我很忙。
根据您愿意投入的预算(时间和/或精力),使用后台工作人员和一些报告 GUI 肯定是一个优点。但这取决于您根据您的应用程序。
例如,我目前正在修改一个拥有 3 个用户的内部应用程序。在这种情况下,沙漏就可以了:他们三个很快就会知道他们只需要等待。不要误会我的意思:这个应用程序非常重要。没有它,使用它的小公司就会消亡。但如果我要求他们额外预算 2 小时来制作一个漂亮且经过测试的小 GUI、后台线程、等等与沙漏,你认为他们会说什么?
另一方面,如果这是您旗舰产品中的一项重要操作,当然要善待您的用户!不要犹豫:后台线程。特别是如果操作实际花费的时间可能比这 5 秒长得多。
结论:务实!
The cheapest way to handle the problem is to turn the cursor into an hourglass during the processing. That tells user please wait, I'm busy.
According to the budget (time and/or effort) you're willing to throw in it, using a backgroundworker and some reporting GUI is certainly a plus. But it's up to you according to your app.
For example, I'm currently modifying an in-house app that has 3 users. In that case, the hourglass is OK: All 3 of them will quickly learn they just have to wait. Don't get me wrong: this app is damn important. Without it, the small company that uses it would just die. But if I ask them for 2 hours of extra budget for a nice and tested little GUI, background thread, blah vs an hourglass, what do you think they'll say?
On the other hand, if it's an important operation in your flagship product, of course be nice to your users! Don't hesitate: background thread. Especially if the operation may actually take much longer than those 5 seconds.
Conclusion: Be pragmatic!
如果您使用 .NET 4.0,我会将其放入后台工作程序或任务火灾中,例如:
I would put it into a background worker or fire of a task if you are in .NET 4.0, for example:
我将投票支持后台工作进程,因为冻结的 UI 就像冻结的应用程序,大多数用户会认为您的应用程序根本没有执行任何操作。
用于进度条或某些动画的 UI 线程,通知正在发生的情况的信息文本 + 后台工作线程 = win
I'll vote for the background worker process, since a frozen UI is like a frozen application, and most of users will think your application isn't doing anything at all.
UI thread for a progress bar or some animation, info text noticing what's going on + background worker thread = win
我认为与 UI 本身无关的每个进程都应该作为单独的线程启动,或者在本例中作为 bg 工作线程启动。这将有助于保持应用程序的健康并易于将来改进/修复。
另外,作为用户或测试人员,我真的很讨厌轻弹和冻结窗口......
问候。
I think every process not related with the UI itself should be started as a separate thred or, in this case, as a bg worker. This will help to maintain the app healthy and easy to improve/fix in the future.
Also, as a user or tester, I really hate flicking and freezing windows...
Regards.
一般经验法则是任何需要一秒或更长时间才能完成的操作都需要向用户提供某种形式的反馈。这可以是进度条、消息等。任何比这更长的时间用户都会感到沮丧(不确定他们是否做错了什么,讨厌等待等)。
对于这样的操作,根据环境(应用程序数量、可用内存、数据大小、硬盘速度等)可能需要更长的时间,它们应该始终放在后台线程上,并将消息通过管道传输回 UI。我喜欢这个 BackGroundWorker。
A general rule of thumb is any operation that takes a second or longer to complete requires some form of feedback to the user. This can be a progress bar, message, etc. Anything longer then that then the user becomes frustrated (not sure if they did something wrong, hate waiting, etc).
For operations like this that can take longer based on the environment (number of apps, available memory, data size, hard drive speed, etc) they should ALWAYS be put on a background thread and pipe messages back to the UI. I love the BackGroundWorker for this.