C# 用c语言并行实现数据排序
因此,为了好玩,我在ubuntu虚拟机上设置了一个ssh蜜罐,并希望对最常用的密码和最常用的用户密码组合进行排序。 我写了一些在工作时花了相当长时间的东西,甚至考虑到日志文件有178.000多行。 所以我决定尝试多线程。我尝试使用Parallel.ForEach。 这是一团糟,没有把整个事情写进结果文件。我在谷歌上搜索了一些东西,最终找到了一些关于并发的东西。 现在可以了,但不是我想要的方式。它将数据写入最常用密码.datmpp和最常用组合.datmpc这两个文件,但根据列表中出现的情况,它们既不是升序,也不是降序。 我知道排序是有效的,因为它只适用于单线程foreach循环 这是迄今为止我一直在努力不去评判的代码,我还在上高中,我知道它可能看起来很凌乱,如果我能让它发挥作用,我会努力把它整理一下C# 用c语言并行实现数据排序,c#,multithreading,sorting,parallel-processing,C#,Multithreading,Sorting,Parallel Processing,因此,为了好玩,我在ubuntu虚拟机上设置了一个ssh蜜罐,并希望对最常用的密码和最常用的用户密码组合进行排序。 我写了一些在工作时花了相当长时间的东西,甚至考虑到日志文件有178.000多行。 所以我决定尝试多线程。我尝试使用Parallel.ForEach。 这是一团糟,没有把整个事情写进结果文件。我在谷歌上搜索了一些东西,最终找到了一些关于并发的东西。 现在可以了,但不是我想要的方式。它将数据写入最常用密码.datmpp和最常用组合.datmpc这两个文件,但根据列表中出现的情况,它们既
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
using System.Collections.Specialized;
using System.Threading;
using System.Collections.Concurrent;
namespace ConsoleApp1
{
public class m
{
public static List<string> passwords = new List<string>();
public static List<string> up = new List<string>();
public static void mpcF()
{
var mpc = new ConcurrentBag<string>();
var dictionary = up.GroupBy(str => str)
.ToDictionary(group => group.Key, group => group.Count());
var items = from pair in dictionary
orderby pair.Value descending
select pair;
Parallel.ForEach(items, item =>
{
mpc.Add((item.Key.PadRight(45) + " | " + item.Value/* + Environment.NewLine*/));
});
var result = string.Join(Environment.NewLine, mpc);
File.WriteAllText("mpc.dat", result);
Console.WriteLine("DUN-DUN-DUUNNN!!!!");
}
public static void mppF()
{
var mpp = new ConcurrentBag<string>();
var dictionary = passwords.GroupBy(str => str)
.ToDictionary(group => group.Key, group => group.Count());
var items = from pair in dictionary
orderby pair.Value descending
select pair;
Parallel.ForEach(items, item =>
{
mpp.Add((item.Key.PadRight(45) + " | " + item.Value/* + Environment.NewLine*/));
});
var result = string.Join(Environment.NewLine, mpp);
File.WriteAllText("mpp.dat", result);
Console.WriteLine("DUN-DUN-DUUNNN!!!! (2)");
}
}
class Program
{
static void read()
{
using (StreamReader sr = new StreamReader("ssh-honeypot.log"))
{
while (!sr.EndOfStream)
{
string[] t = sr.ReadLine().Split(']')[1].Split(' ');
if (t[2] != "Error")
{
m.passwords.Add(t[3]);
m.up.Add(t[2] + " - " + t[3]);
}
}
}
}
static void print()
{
m.mpcF();
m.mppF();
/*Thread t1 = new Thread(new ThreadStart(m.mpcF));
Thread t2 = new Thread(new ThreadStart(m.mppF));
t1.Start();
t2.Start();*/
}
static void Main(string[] args)
{
read();
print();
Console.ReadKey();
}
}
}
它们不按顺序排列的原因是由于以下代码:
public static void mppF()
Parallel.ForEach(items, item =>
{
mpp.Add((item.Key.PadRight(45) + " | " + item.Value/* + Environment.NewLine*/));
});
Parallel.ForEach将有多个线程在列表上工作,每个线程将向ConcurrentBag的输出集合添加内容。对于多个线程,无法保证哪个线程将获得哪个项目,或者线程将以什么顺序处理这些项目。所以你要做的就是把一个分类的集合放到你的物品列表中,然后把它置乱
很难想象只有178000件物品需要相当长的时间。在一个线程中,您应该能够在几秒钟内完成这项工作,可能更少。例如,您可以这样做:
public static void mppF()
{
var orderedByCount = passwords
.GroupBy(str => str) // group by password
.Select(g => new { Key = g.Key, Count = g.Count()) // select key and count
.OrderBy(pair => pair.Count) // sort
.Select(pair => string.Format("{0:-45} | {1}", pair.Key, pair.Count); // construct output string
File.WriteAllLines("mpp.dat", passwords);
Console.WriteLine("DUN-DUN-DUUNNN!!!! (2)");
}
您的其他功能也可以进行类似的优化
您可以通过向查询添加一个AsParallel调用来并行化,如下所示:
var orderedByCount = passwords
.AsParallel()
.GroupBy(str => str) // group by password
.Select(g => new { Key = g.Key, Count = g.Count()) // select key and count
.OrderBy(pair => pair.Count) // sort
.Select(pair => string.Format("{0:-45} | {1}", pair.Key, pair.Count); // construct output string
如果我正确地阅读了文档,应该可以保持秩序。尽管如此,很有可能只有178000项,顺序查询的执行速度会更快。您想并行执行什么?解析、排序或重构位?从一个长期编写代码的人那里,我知道解决这类问题的答案几乎从来都不是多线程。这是解决正确问题的强大工具,但你真的需要知道自己在做什么。如果您想知道为什么您的程序很慢,那么您可以使用StopWatch类测量代码的各个部分,并查看需要花费的时间:谢谢!我一定要试试!今天我有一个想法,我将尝试修改蜜罐的脚本,这样它就不会写入日志文件,而是将数据发送到mysql数据库。今天我要两种方法都试试!不要指望数据库比顺序文件快。