假设我有这个 python 代码:
def double_inputs():
while True:
x = yield
yield x * 2
gen = double_inputs()
next(gen)
print(gen.send(1))
Run Code Online (Sandbox Code Playgroud)
正如预期的那样,它打印“2”。我可以像这样在 c++20 中制作一个生成器:
#include <coroutine>
template <class T>
struct generator {
struct promise_type;
using coro_handle = std::coroutine_handle<promise_type>;
struct promise_type {
T current_value;
auto get_return_object() { return generator{coro_handle::from_promise(*this)}; }
auto initial_suspend() { return std::suspend_always{}; }
auto final_suspend() { return std::suspend_always{}; }
void unhandled_exception() { std::terminate(); }
auto yield_value(T value) {
current_value = value;
return std::suspend_always{};
}
};
bool next() { return coro …Run Code Online (Sandbox Code Playgroud) 是否可以序列化包含yield语句的方法(或包含此类方法的类),以便在对类进行重新水化时,保留生成的迭代器的内部状态?
我目前正处于个人学习项目中,我在XML数据库中阅读.我发现自己正在编写收集数据的函数,我不确定什么是快速返回它们的方法.
这通常更快:
yields,或 append()在功能中的几个s然后return随后list?我很高兴知道在什么情况下yields会比append()s 快,反之亦然.
下面是一个示例代码,用于使用我在google搜索时在几个地方找到的yield关键字从数据库中检索数据:
public IEnumerable<object> ExecuteSelect(string commandText)
{
using (IDbConnection connection = CreateConnection())
{
using (IDbCommand cmd = CreateCommand(commandText, connection))
{
connection.Open();
using (IDbDataReader reader = cmd.ExecuteReader())
{
while(reader.Read())
{
yield return reader["SomeField"];
}
}
connection.Close();
}
}
}
Run Code Online (Sandbox Code Playgroud)
我是否认为在此示例代码中,如果我们不遍历整个datareader,连接将不会被关闭?
如果我理解正确的收益,这是一个不会关闭连接的例子.
foreach(object obj in ExecuteSelect(commandText))
{
break;
}
Run Code Online (Sandbox Code Playgroud)
对于可能不是灾难性的数据库连接,我想GC最终会将其清理干净,但是如果不是连接它会是一个更关键的资源呢?
我正在编写重构Silverlight程序,以从WCF服务中消耗其现有业务逻辑的一部分.在这样做时,我遇到了Silverlight 3中的限制,它只允许对WCF服务的异步调用,以避免长时间运行或无响应的服务调用阻塞UI线程(SL有一个有趣的排队模型来调用WCF服务)在UI线程上).
因此,编写曾经很简单的东西变得越来越复杂(请参阅我的问题末尾的代码示例).
理想情况下,我会使用协同程序来简化实现,但遗憾的是,C#目前不支持协同程序作为本机语言工具.但是,C#确实具有使用yield return语法的生成器(迭代器)的概念.我的想法是重新使用yield关键字,以允许我为相同的逻辑构建一个简单的协同模型.
但是,我不愿意这样做,因为我担心可能存在一些我没有预料到的隐藏(技术)陷阱(考虑到我对Silverlight和WCF的相对缺乏经验).我也担心未来的开发人员可能不清楚实现机制,并且可能会阻碍而不是简化他们将来维护或扩展代码的努力.我已经在SO上看到了关于重构迭代器以构建状态机的问题:使用"yield"关键字实现状态机,虽然它与我正在做的事情不完全相同,但它确实让我停下来.
但是,我需要做一些事情来隐藏服务调用的复杂性,并管理此类更改中的缺陷的工作量和潜在风险.我对可以用来解决这个问题的其他想法或方法持开放态度.
原始的非WCF版本的代码看起来像这样:
void Button_Clicked( object sender, EventArgs e ) {
using( var bizLogic = new BusinessLogicLayer() ) {
try {
var resultFoo = bizLogic.Foo();
// ... do something with resultFoo and the UI
var resultBar = bizLogic.Bar(resultFoo);
// ... do something with resultBar and the UI
var resultBaz = bizLogic.Baz(resultBar);
// ... do something with resultFoo, resultBar, resultBaz
}
}
}
Run Code Online (Sandbox Code Playgroud)
重新考虑的WCF版本变得更加复杂(即使没有异常处理和前/后条件测试):
// fields needed to …Run Code Online (Sandbox Code Playgroud) 目前我正在阅读David A. Black的"The Well-Grounded Rubyist",我坚持10.9章(枚举器和可枚举的下一个维度).我的问题是关于yield方法.yieldRuby上下文中单词的含义是什么?我的母语是俄语,谷歌翻译向我展示了一堆翻译变体,让我感到困惑.其中有一些:给予,带来,投降(放弃),生产,同意,遵守和许多其他人.
UPD:请注意这个事实,我试图理解Enumerator :: Yielder#yield方法的含义 ,但不是yield关键字本身.
UPD_2:我发现了有关枚举器的有趣文章:" Ruby中的懒惰枚举器 ".
关于Scala中的yield命令和以下示例:
val values = Set(1, 2, 3)
val results = for {v <- values} yield (v * 2)
Run Code Online (Sandbox Code Playgroud)
PS.我知道这个例子没有遵循推荐的功能方式(也就是使用map),但它只是一个例子.
我有一个很长的循环过程,如下所示:
public void Process()
{
bool done = false;
do {
//do stuff
}while (!done);
}
Run Code Online (Sandbox Code Playgroud)
我想切入比特并让调用例程在某种UI中显示我的进度.它是一个类库,因此调用者可能是任何东西(Console App,WinForms,WebApp,...).
如果我能做的话,这将是最简单的:
public void Process()
{
bool done = false;
do {
//do stuff
yield return;
}while (!done);
}
Run Code Online (Sandbox Code Playgroud)
因此调用者可以继续调用该方法,直到完成为止.
这更像是BackgroundWorker的工作,但对于控制台应用来说这似乎是"错误的"......我不会总是需要多线程.或者是吗?我的意思是,是的,我可以让控制台的主线程等待它完成.
我的问题是:我可以使用"收益回报"的"零碎"延迟执行功能而不实际返回某些内容吗?
是否有单行表达式:
for thing in generator:
yield thing
Run Code Online (Sandbox Code Playgroud)
我试着yield generator无济于事.
我试图在一天之内使用Python和Scrapy从所有国家的所有机场取消所有出发和到达.
这个着名站点(飞行雷达)使用的JSON数据库需要在一个机场的出发或到达> 100时逐页查询.我还根据查询的实际UTC计算时间戳.
我尝试使用此层次结构创建数据库:
country 1
- airport 1
- departures
- page 1
- page ...
- arrivals
- page 1
- page ...
- airport 2
- departures
- page 1
- page ...
- arrivals
- page
- page ...
...
Run Code Online (Sandbox Code Playgroud)
我使用两种方法按页面计算时间戳和网址查询:
def compute_timestamp(self):
from datetime import datetime, date
import calendar
# +/- 24 heures
d = date(2017, 4, 27)
timestamp = calendar.timegm(d.timetuple())
return timestamp
def build_api_call(self,code,page,timestamp):
return 'https://api.flightradar24.com/common/v1/airport.json?code={code}&plugin\[\]=&plugin-setting\[schedule\]\[mode\]=&plugin-setting\[schedule\]\[timestamp\]={timestamp}&page={page}&limit=100&token='.format(
code=code, page=page, timestamp=timestamp)
Run Code Online (Sandbox Code Playgroud)
我将结果存储到CountryItem包含许多AirportItem机场的结果中.我 …
yield ×10
python ×4
c# ×3
.net ×2
asynchronous ×2
generator ×2
.net-2.0 ×1
c++ ×1
c++20 ×1
collections ×1
enumerable ×1
feedback ×1
performance ×1
point ×1
python-2.7 ×1
recursion ×1
return ×1
ruby ×1
scala ×1
scrapy ×1
wcf ×1
web-scraping ×1
yield-return ×1