C# 数据库异步查询与处理
让我重新措辞 我有一个方法,在给定开始字符串(路径)后生成字符串(路径) 如果这些路径是针对某个目录的,我想将其放入方法输入的队列中 在同步处理路径之后,我希望获取数据并将其异步克隆到管道的多个路径中,每个路径都需要获取数据块。所以Broadcastblock是不可能的(它不能在自身之前向块发送阻塞信号), joinblock,连接结果是相对直接的 总而言之 数据流块中是否有一个块,我可以在其中从委托访问inputqueue,如果何时,如何? 是否有一个构造的行为类似于broadcastblock,但可以阻止之前的块 我试着通过全能的谷歌做到这一点:C# 数据库异步查询与处理,c#,asynchronous,pipeline,sharpsvn,tpl-dataflow,C#,Asynchronous,Pipeline,Sharpsvn,Tpl Dataflow,让我重新措辞 我有一个方法,在给定开始字符串(路径)后生成字符串(路径) 如果这些路径是针对某个目录的,我想将其放入方法输入的队列中 在同步处理路径之后,我希望获取数据并将其异步克隆到管道的多个路径中,每个路径都需要获取数据块。所以Broadcastblock是不可能的(它不能在自身之前向块发送阻塞信号), joinblock,连接结果是相对直接的 总而言之 数据流块中是否有一个块,我可以在其中从委托访问inputqueue,如果何时,如何? 是否有一个构造的行为类似于broadcastbloc
class subversion
{
private static string repo;
private static string user;
private static string pw;
private static DateTime start;
private static DateTime end;
private static List<parserObject> output;
public static List<parserObject> svnOutputList
{
get {return output; }
}
private static List<string> extension_whitelist;
public async void run(string link, string i_user, string i_pw, DateTime i_start, DateTime i_end)
{
repo = link;
user = i_user;
pw = i_pw;
start = i_start;
end = i_end;
output = new List<parserObject>();
BufferBlock<string> crawler_que = new BufferBlock<string>();
BufferBlock<svnFile> parser_que = new BufferBlock<svnFile>();
var svn = crawl(crawler_que, parser_que);
var broadcaster = new ActionBlock<svnFile>(async file =>
{//tried to addapt the code from this ensure always send broadcastblock -> see link below
List<Task> todo = new List<Task>();
todo.Add(mLoc);//error cannot convert methodgroup to task
foreach (var task in todo)//error: Only assignment, call, increment, decrement, await, and new object expressions can be used as a statement?
{
task.SendAsync(file);//error cannot convert task to targetblock
}
await Task.WhenAll(todo.ToArray());
});
parser_que.LinkTo(broadcaster);
await Task.WhenAll(broadcaster, svn);//error cannot convert actionblock to task
}
private static async Task crawl(BufferBlock<string> in_queue, BufferBlock<svnFile> out_queue)
{
SvnClient client = new SvnClient();
client.Authentication.ForceCredentials(user, pw);
SvnListArgs arg = new SvnListArgs
{
Depth = SvnDepth.Children,
RetrieveEntries = SvnDirEntryItems.AllFieldsV15
};
while (await in_queue.OutputAvailableAsync())
{
string buffer_author = null;
string prev_author = null;
System.Collections.ObjectModel.Collection<SvnListEventArgs> contents;
string link = await in_queue.ReceiveAsync();
if (client.GetList(new Uri(link), arg, out contents))
{
foreach (SvnListEventArgs item in contents)
{
if (item.Entry.NodeKind == SvnNodeKind.Directory)
{
in_queue.Post(item.Path);
}
else if (item.Entry.NodeKind == SvnNodeKind.File)
{
try
{
int length = item.Name.LastIndexOf(".");
if (length <= 0)
{
continue;
}
string ext = item.Name.Substring(length);
if (extension_whitelist.Contains(ext))
{
Uri target = new Uri((repo + link));
SvnRevisionRange range;
SvnBlameArgs args = new SvnBlameArgs
{
Start = start.AddDays(-1),
End = end
};
try
{
svnFile file_instance = new svnFile();
client.Blame(target, args, delegate(object sender3, SvnBlameEventArgs e)
{
if (e.Author != null)
{
buffer_author = e.Author;
prev_author = e.Author;
}
else
{
buffer_author = prev_author;
}
file_instance.lines.Add(new svnLine(buffer_author, e.Line));
});
out_queue.Post(file_instance);
}
catch (Exception a) { Console.WriteLine("exception:" + a.Message);}
}
}
catch (Exception a)
{
}
}
}
}
}
}
private static async Task mLoc(svnFile file)
{
List<parserPart> parts = new List<parserPart>();
int find;
foreach (svnLine line in file.lines)
{
if ((find = parts.FindIndex(x => x.uploader_id == line.author)) > 0)
{
parts[find].count += 1;
}
else
{
parts.Add(new parserPart(line.author));
}
find = 0;
}
parserObject ret = new parserObject(parts, "mLoc");
await output.Add(ret);
return;
}
}
类颠覆
{
私人静态字符串回购;
私有静态字符串用户;
私有静态字符串pw;
私有静态日期时间开始;
私有静态日期时间结束;
私有静态列表输出;
公共静态列表svnOutputList
{
获取{返回输出;}
}
私有静态列表扩展_白名单;
公共异步无效运行(字符串链接、字符串i_用户、字符串i_pw、日期时间i_开始、日期时间i_结束)
{
回购=链接;
用户=i_用户;
pw=i_pw;
开始=i_开始;
结束=i_结束;
输出=新列表();
BufferBlock crawler_que=新的BufferBlock();
BufferBlock解析器_que=新的BufferBlock();
var svn=爬网(爬网程序、解析器);
var广播=新操作块(异步文件=>
{//试图添加此代码,请确保始终发送广播块->参见下面的链接
List todo=新列表();
todo.Add(mLoc);//错误无法将methodgroup转换为任务
foreach(todo中的var task)//错误:只能将赋值、调用、递增、递减、等待和新对象表达式用作语句?
{
task.SendAsync(文件);//错误无法将任务转换为targetblock
}
等待Task.WhenAll(todo.ToArray());
});
解析链接(广播公司);
wait Task.WhenAll(广播机,svn);//错误无法将actionblock转换为任务
}
专用静态异步任务爬网(BufferBlock in_队列,BufferBlock out_队列)
{
SvnClient client=新的SvnClient();
client.Authentication.ForceCredentials(用户,pw);
SvnListArgs arg=新SvnListArgs
{
深度=SvnDepth.子对象,
RetrieveEntries=SvnDirEntryItems.AllFieldsV15
};
while(在_queue.OutputAvailableAsync()中等待)
{
字符串缓冲区\u author=null;
字符串prev_author=null;
System.Collections.ObjectModel.Collection内容;
string link=wait in_queue.ReceiveAsync();
if(client.GetList(新Uri(链接)、arg、out内容))
{
foreach(目录中的SvnListEventArgs项)
{
if(item.Entry.NodeKind==SvnNodeKind.Directory)
{
in_queue.Post(item.Path);
}
else if(item.Entry.NodeKind==SvnNodeKind.File)
{
尝试
{
int length=item.Name.LastIndexOf(“.”);
如果(长度x.uploader_id==line.author))>0)
{
零件[find]。计数+=1;
}
其他的
{
Add(新的parserPart(line.author));
}
find=0;
}
parserObject ret=新的parserObject(部分,“mLoc”);
等待输出。添加(ret);
返回;
}
}
广播块回答:在#1中,您声明了一个名为
string
的参数,它恰好是string类型。如果是这样的话,您可以将其命名为path
。至于#2,您的意思是什么?您是否尝试创建并链接两个不同的TransformBlock,一个用于GetFile,另一个用于ProcessFile?例如,TransformBlock
和aTransformBlock
?关于队列的问题也令人困惑-TransformBlocks已经缓冲了它们的输入。请发布您尝试的实际代码。这几乎就是我使用的代码,我试图稍微弄乱它,并且知道broadcastblock完全被破坏了=(该输入
从何而来?它应该包含什么?块的实际输入是路径
参数,实际上没有在任何地方使用。您不需要自己访问输入缓冲区,TransformBlock会为您执行此操作。是否要向块发布repo链接?输入变量是块的其余部分bufferblock测试,但这与我的问题无关,我的问题是,我如何从内部访问转换块输入que,还是需要将爬虫部分放入转换块中?你刚刚破坏了问题,使答案不可能。无论如何,你完全没有抓住要点。那就是输入
块的输入。您不需要做任何事情就可以访问它。如果您在该块上调用Post(someURL),则将使用包含您发布的URL的INPUT
参数调用lambda。从lambda返回的任何内容都将传递到下一个块