2011-08-24 93 views
0

我想实现一个解决方案,我得到另一个问题,我问(http://stackoverflow.com/questions/7166223/create-password-breaker-for-iphone-backup-files)。解决方案非常简单。问题是我正在使用一本包含大约25万字的字典。对于每个单词,我都会添加特定模式的字母和数字,以获得我通常使用的不同组合。我已经拿走了我很少使用的组合,但每个单词仍然有大约24个组合,因此最终的单词列表将会是600万左右。是否有可能通过文件将循环拆分成多个线程?

创建列表的过程非常缓慢。我在想,如果多线程可以解决我的问题。我的理论是,我可以说4线程(我是线程新手,不知道这是否可能)。在线程1中,我使用字典的第一个四分之一,在线程2和第二个四分之一中,依此类推。每个线程循环遍历字典中的单词,并添加不同的组合。当每个线程完成时,它会将结果写入线程特定的文本文件。当所有的线程完成他们的工作后,我会将不同的文件连接成一个大的文本文件(其中包含所有600万字)。从而减少处理时间4.至少这是我所希望的。 :=)

我正在C#中工作。这可能吗?所以简而言之:是否可以在C#中使用不同的线程遍历文本文件的不同部分?有什么特别的我应该考虑一下吗?

我会尝试尝试使用它,但任何建议你可能有高度赞赏。

回答

2

这很有可能,假设你有一个快速的方法来划分名单(我认为打破中间词将是不好的)。

但是,请记住,线程什么也不做,除非您有足够的备用处理能力才能使用。如果您使用的是单CPU /单核PC,则可以尽可能快地进行。但是,如果你有多个CPU(或者至少有多个内核),那么这是一个机会。

实现相当简单。如果你现在正在做的:

ProcessText(fullTextBlock); 

那么它只是:

ThreadPool.QueueUserWorkItem(ProcessText, textBlock1); 
ThreadPool.QueueUserWorkItem(ProcessText, textBlock2); 
ThreadPool.QueueUserWorkItem(ProcessText, textBlock3); 
ThreadPool.QueueUserWorkItem(ProcessText, textBlock4); 
+0

非常感谢您的非常快的答案詹姆士! :=)恐怕我在单核PC上。所以使用单核电脑时不能使用多线程?我的想法是有4种不同的方法:getPassword1(),getPassword2()等。不是非常面向对象,因为他们会做同样的事情。但这只是这一次(HOPEFULLY; =)),所以我认为这可能是一个简单的解决方案。然后我会让每个线程调用它自己独立的方法。但如果我了解你,那是不可能的? – SwedishDotNetProgrammer

+0

嘿詹姆斯!我创建了一个简单的控制台应用程序,我可以选择想要使用的线程数。我试图使用100个线程,它运行良好。我编写了一些时间来处理一定数量的单词,并且在使用多个线程时大大减少了时间。为了避免冲突,我将原始密码文件分成了相等的部分。每个线程根据其部分创建密码,然后将结果写入其自己的文件。 仅当与线程可能构成威胁的相同方法和变量进行交互时才会发生? – SwedishDotNetProgrammer

+0

詹姆斯,我没有足够的“信誉”在这里stackoverflow upvote你的答案,但这里是从我的赞许! :=) – SwedishDotNetProgrammer

0

由于这是我在使用线程的第一次尝试,我想我可能会分享我实现了解决方案。如果任何人有任何关于如何改善这个问题的建议,那将会很棒。我对线程的理解是,当它们与相同的方法或变量进行交互时,使用线程可能是一个大问题。但我认为我完全分开了线程。他们正在使用我创建的类的不同实例。所以如果有人在使用线程的方式上有一些很好的建议,我很高兴。 :=)这是我用来渲染线程的代码:

for (int i = 0; i < threads; i++) 
      { 
       string errorFileName = "errorFile" + (i + 1) + ".dic"; 
       string saveFileName = "english" + (i + 1) + ".dic"; 
       string logfileName = "error.log"; 
       string[] currentContent; 
       if (i != threads - 1) 
       { 
        currentContent = contentArrayOriginal.Skip(skipStrings).Take(takeStrings).ToArray(); 
       } 
       else 
       { 
        int skip = skipStrings; 
        int take = numberOfWords - skip; 
        currentContent = contentArrayOriginal.Skip(skip).Take(take).ToArray(); 
       } 
       PasswordRendering passRender = new PasswordRendering(rootFilePath, errorFilePath, dictionariesFilePath, currentContent, versionsMain, errorFileName, saveFileName, logfileName, (i + 1)); 
       Thread thread = new Thread(new ThreadStart(passRender.SetPasswords)); 
       thread.Start(); 
       skipStrings += takeStrings; 
      } 

这里是代码,节省了渲染的密码(在PasswordRendering类):

File.WriteAllText(dictionariesFilePath + saveFileName, newContent); 
相关问题