- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
更新:我已经准备好了可以无问题地再现问题的示例,请使用以下URL下载测试项目:
https://www.dsr-company.com/fm.php?Download=1&FileToDL=DeadLockTest_CoreDataWithoutMR.zip
提供的项目存在以下问题:提取时发生死锁
在performBlockAndWait中从主线程调用。
如果使用XCode版本> 6.4编译代码,则会重现此问题。
如果使用xCode == 6.4编译代码,则不会重现此问题。
老问题是:
我正在为IOS移动应用程序提供支持。
在最近将Xcode IDE从6.4版更新到7.0版(具有IOS 9支持)之后,我遇到了关键问题-应用程序挂起。
与xCode 6.4相同的应用程序构建(由相同的资源生成)可以正常工作。
因此,如果使用xCode> 6.4构建应用程序,则在某些情况下应用程序会挂起。
如果应用程序是使用xCode 6.4构建的,则该应用程序可以正常工作。
我花了一些时间研究问题,结果,我准备了具有类似情况的测试应用程序,就像在重现问题的应用程序中一样。
测试应用程序在Xcode> = 7.0上挂断,但在Xcode 6.4上正常运行
测试源下载链接:
https://www.sendspace.com/file/r07cln
测试应用程序的要求是:
1.必须在系统中安装 cocoa pod 管理器
2. 2.2版的MagicalRecord框架。
测试应用程序以以下方式工作:
1.在应用程序启动时,它将创建具有10000条简单实体记录的测试数据库,并将其保存到持久性存储中。
2.在应用程序的第一个屏幕上的viewWillAppear方法中:它运行导致死锁的测试。
使用以下算法:
-(NSArray *) entityWithId: (int) entityId inContext:(NSManagedObjectContext *)localContext
{
NSArray * results = [TestEntity MR_findByAttribute:@"id" withValue:[ NSNumber numberWithInt: entityId ] inContext:localContext];
return results;
}
…..
int entityId = 88;
NSManagedObjectContext *childContext1 = [NSManagedObjectContext MR_context];
childContext1.name = @"childContext1";
NSManagedObjectContext *childContext2 = [NSManagedObjectContext MR_context];
childContext2.name = @"childContext2";
NSArray *results = [self entityWithId:entityId inContext: childContext2];
for(TestEntity *d in results)
{
NSLog(@"e from fetchRequest %@ with name = '%@'", d, d.name); /// this line is the reason of the hangup
}
dispatch_async(dispatch_get_main_queue(), ^
{
int entityId2 = 11;
NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"id=%d", entityId2];
NSArray *a = [ TestEntity MR_findAllWithPredicate: predicate2 inContext: childContext2];
for(TestEntity *d in a)
{
NSLog(@"e from fetchRequest %@ with name = '%@'", d, d.name);
}
});
最佳答案
这就是为什么我不使用抽象(即隐藏)太多核心数据细节的框架的原因。它具有非常复杂的使用模式,有时您需要了解它们如何互操作的详细信息。
首先,我对魔术唱片一无所知,只是很多人都在使用它,因此它必须非常擅长它的工作。
但是,在您的示例中,我立即看到核心数据并发的几种完全错误的用法,因此我去看了看头文件,以了解为什么您的代码做出了假设。
我根本不是要打你,尽管乍一看似乎有点像。我想帮助您进行教育(我以此为契机来窥视MR)。
快速浏览MR,我想说您对MR的功能以及核心数据的一般并发规则有一些误解。
首先,你这样说...
Two managed object contexts are created with concurrency type == NSPrivateQueueConcurrencyType (please check the code of MR_context of magical record framework). Both contexts has parent context with concurrency type = NSMainQueueConcurrencyType.
MR_rootSavingContext
,它本身也是私有(private)队列上下文。
NSManagedObjectContext *childContext1 = [NSManagedObjectContext MR_context];
childContext1.name = @"childContext1";
NSManagedObjectContext *childContext2 = [NSManagedObjectContext MR_context];
childContext2.name = @"childContext2";
childContext1
和
childContext2
),它们都是另一个匿名私有(private)队列MOC的子代(我们将称为
savingContext
)。
NSArray *results = [self entityWithId:entityId inContext: childContext2];
childContext1
执行获取。该代码实际上是...
-(NSArray *) entityWithId:(int)entityId
inContext:(NSManagedObjectContext *)localContext
{
NSArray * results = [TestEntity MR_findByAttribute:@"id"
withValue:[NSNumber numberWithInt:entityId]
inContext:localContext];
return results;
}
localContext
是指向
childContext2
的另一个指针,它是私有(private)队列MOC。在对
performBlock
的调用之外访问私有(private)队列MOC是违反并发规则的100%。但是,由于您正在使用另一个API,并且方法名称无法帮助您了解如何访问MOC,因此我们需要查看该API并查看它是否隐藏了
performBlock
,以查看您是否正确访问了它。
MR_executeFetchRequest...
,后者在文档中也未指示它如何处理并发。因此,我们来看一下它的实现。
performBlockAndWait
,它将在调用时阻塞。
performBlockAndWait
。我自己的个人规则是
,除非绝对没有其他选择,否则切勿使用
performBlockAndWait
。
for(TestEntity *d in results)
{
NSLog(@"e from fetchRequest %@ with name = '%@'", d, d.name); /// this line is the reason of the hangup
}
MR_
方法的培训,这些方法不需要并发模型的知识,因此您会忘记或永远不会学习并发规则。
results
数组中的对象都是生活在
childContext2
私有(private)队列上下文中的所有托管对象。因此,如果您不对并发规则表示敬意,则可能永远无法访问它们。这显然违反了并发规则。在开发应用程序时,应使用参数-com.apple.CoreData.ConcurrencyDebug 1启用并发调试。
performBlock
或
performBlockAndWait
中。我几乎没有用过
performBlockAndWait
,因为它有很多缺点-死锁就是其中之一。实际上,仅看到
performBlockAndWait
的使用就非常有力地表明您的死锁正在那里发生,而不是在您所指示的代码行上发生。但是,在这种情况下,它至少与先前的提取一样安全,因此让我们使其更加安全...
[childContext2 performBlockAndWait:^{
for (TestEntity *d in results) {
NSLog(@"e from fetchRequest %@ with name = '%@'", d, d.name);
}
}];
dispatch_async(dispatch_get_main_queue(), ^{
int entityId2 = 11;
NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"id=%d", entityId2];
NSArray *a = [TestEntity MR_findAllWithPredicate:predicate2
inContext:childContext2];
for (TestEntity *d in a) {
NSLog(@"e from fetchRequest %@ with name = '%@'", d, d.name);
}
});
performBlockAndWait
,但是您随后在for循环中进行的访问再次违反了核心数据并发规则。
performBlockAndWait
的使用,因为这只是一个等待发生的问题。 MR_defaultContext
用作使用
MR_context
创建的所有MOC的父级。因此,默认的MOC确实是主队列MOC,现在这一切都变得很合理了。
performBlockAndWait
,这是一个很大的禁止,几乎可以保证您会遇到死锁。
performBlockAndWait
。至少在我看来,将其用作您下面的API的一部分更加可怕。
performBlockAndWait
,然后在尝试执行提取时必须锁定其父上下文。
performBlockAndWait
。
performBlockAndWait
。
- (void)executeFetchRequest:(NSFetchRequest *)request
inContext:(NSManagedObjectContext *)context
completion:(void(^)(NSArray *results, NSError *error))completion
{
[context performBlock:^{
NSError *error = nil;
NSArray *results = [context executeFetchRequest:request error:&error];
if (completion) {
completion(results, error);
}
}];
}
NSFetchRequest *request = [[NSFetchRequest alloc] init];
[request setEntity: testEntityDescription ];
[request setPredicate: predicate2 ];
[self executeFetchRequest:request
inContext:childContext2
completion:^(NSArray *results, NSError *error) {
if (results) {
for (TestEntity *d in results) {
NSLog(@"++++++++++ e from fetchRequest %@ with name = '%@'", d, d.name);
}
} else {
NSLog(@"Handle this error: %@", error);
}
}];
关于ios - xCode 7.0 IOS9 SDK : deadlock while executing fetch request with performBlockAndWait,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32887919/
我正在运行此代码并在没有互联网连接的情况下进行测试: fetch(url, options) .then(res => { // irrelevant, as catch happens
function fetchHandler(evt) { console.log('request:' + evt.request.url); dealWithRequest(evt)
我在 AdventureWorks2016 上执行了两个示例查询,并得到了相同的结果。那么什么时候应该使用 NEXT 或 FIRST 关键字? select LastName + ' ' + Firs
我有以下查询: @Query("SELECT new de.projectemployee.ProjectEmployee(employee) " + "FROM ProjectEmpl
我正在尝试使用 fetch on react 来实现客户端登录。 我正在使用护照进行身份验证。我使用的原因 fetch而不是常规 form.submit() , 是因为我希望能够从我的快速服务器接收错
我正在尝试将我的 Aurelia 项目从 beta 版本升级到 3 月版本。 我遇到的错误之一是: Cannot find name 'Request'. 谷歌搜索会在 GitHub 上显示此问题:h
见标题。在我们的react项目中调用fetch时,一位(现已离职)开发人员最初使用from fetch to window.fetch。我不确定两者之间的区别,也无法在网上找到任何结论(W3Schoo
这个问题在这里已经有了答案: HTTP status code 401 even though I’m sending credentials in the request (1 个回答) How
这是代码片段: var fetch = require("node-fetch"); var fetchMock = require("fetch-mock"); function setupMock
我在这里看到了两种不同的抓取方式: https://github.com/github/fetch https://github.com/matthew-andrews/isomorphic-fetc
以下git命令有什么区别? git fetch origin 和 git fetch --all 从命令行运行它们看起来就像它们做同样的事情。 最佳答案 git fetch origin 仅从 ori
我有一个不断改变值的动态 json。我想用该数据绘制图表所以我将动态数据存储到数组然后用该数组绘制图表。目前我创建了 serinterval 用于从 api 获取新数据。但问题是如果新数据没有,它会再
我有一个很大的 JSON blob,我想预先加载我的网页。为此,我添加了 到我的页面。我也有一个 JS 请求来获取相同的 blob。 这不起作用,控制台报告: [Warning] The resour
我们在单页 JavaScript 应用程序发出 fetch 请求时遇到不一致的客户端错误。值得注意的是,它们都是同源请求。 let request = new Request(url, options
我是 ReactJS 的新手,我一直在阅读如何从 api 获取和发布数据。我见过这两个,但我不知道该用什么以及两者之间有什么区别?我读了它,但我不确定我会用什么。谢谢! react-fetch wha
Doctrine中注解@ManyToOne中的fetch="EAGER"和fetch="LAZY"有什么区别? /** * @ManyToOne(targetEntity="Cart", casca
我想要获取一个 api,然后调用另一个 api。在 javascript 中使用这样的代码是否明智? fetch(url, { method: 'get', }).then(function(re
我有一个组件,它依赖于 2 个端点来检索所需程序的名称。我有 2 个端点。第一个端点返回程序列表,它是一个对象数组。目前,它仅返回 4 个节目(2 个节目 ID 为“13”,另外两个节目 ID 为“1
我的应用程序从外部源(配置文件)接收查询,因此它必须从查询结果中获取列。我有一些代码: typedef union _DbField { text text[512]; sword i
我有一个实体A,它与实体B有对多关系。 Entity A -->> Entity B 我需要在多个屏幕上引用一对多关系的计数。此外,我可以多次从 Entity A
我是一名优秀的程序员,十分优秀!