代码中的package main
import (
"fmt"
"math/rand"
"sync"
"time"
)
type RequestHandler struct {
locker sync.Mutex
concurrentRequests map[string]*sync.Mutex
}
func (h *RequestHandler) DoSomething(id string) {
// obtain a lock
var idLock *sync.Mutex
needlock := true
for needlock {
h.locker.Lock()
if h.concurrentRequests == nil {
h.concurrentRequests = make(map[string]*sync.Mutex)
}
idLock = h.concurrentRequests[id]
// this is the only way to "acquire a lock": to be the one creating it - otherwise if there already
// is a lock we just block until it unlocks and then try again, assuming it will be removed from the
// map any moment and we'll get back to this line again and get to create it
if idLock == nil {
// in this case we are creating the lock, we can safely lock it here without risk of deadlock
idLock = &sync.Mutex{}
h.concurrentRequests[id] = idLock
needlock = false
idLock.Lock()
h.locker.Unlock()
} else {
h.locker.Unlock()
idLock.Lock()
idLock.Unlock()
}
// then try again if we didn't get a lock
}
defer func() {
// sync access to map
h.locker.Lock()
h.concurrentRequests[id] = nil // remove this lock from the set
h.locker.Unlock()
// we're done, let the next guy access this id
idLock.Unlock()
}()
// DO THE WORK HERE
fmt.Println(fmt.Sprintf("Starting work on id '%s'...", id))
// hard at work...
time.Sleep(time.Duration((rand.Int() % 50)) * time.Millisecond)
fmt.Println(fmt.Sprintf("Ending work on id '%s'...", id))
}
func main() {
reqHandler := &RequestHandler{}
for i := 0; i < 1000; i++ {
go reqHandler.DoSomething(fmt.Sprintf("%v", rand.Int()%20))
time.Sleep(5 * time.Millisecond)
}
}
工作正常,但在点击时它不会显示检查图标。有什么想法吗?
NSButtonCell
以下是行动代码:
- (NSCell *)outlineView:(NSOutlineView *)outlineView dataCellForTableColumn:(NSTableColumn *)tableColumn item:(id)item {
if ([[tableColumn identifier] isEqualToString:@"select"]) {
NSButtonCell *cell = [[NSButtonCell alloc]init];
[cell setButtonType:NSSwitchButton];
[cell setTarget:self];
[cell setAction:@selector(checkboxChanged:)];
[cell setTitle:@""];
return cell;
} else {
NSCell *cell = [tableColumn dataCell];
return cell;
}
}
答案 0 :(得分:1)
我不确定为什么你的第一个解决方案不起作用 - 也许你没有让你的代表联系起来?请注意,数据源和委托是两个不同的东西。
您在答案中实施的方法(数据源)不适合这样做。数据源,尤其是numberOfRowsInTableView:
和tableView:objectValueForTableColumn:row:
,应仅返回正在呈现的内容,而不是创建视图/单元格对象。
我建议在你的xib中创建和配置NSButtonCell,如果你有一个,或者在你创建表视图及其列的同一个地方 - 这也是设置每个列的单元格的正确位置。
答案 1 :(得分:0)
我通过将上述代码从NSOutlineView
delegate
方法outlineView: dataCellForTableColumn:item:
更改为delegate
方法outlineView: objectValueForTableColumn: byItem:
像这样:
- (id)outlineView:(NSOutlineView *)outlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item {
if ([[tableColumn identifier] isEqualToString:@"select"]) {
NSButtonCell* cell = [tableColumn dataCell];
[cell setSelectable:YES];
[cell setEnabled:YES];
[cell setTransparent:NO];
[cell setButtonType:NSSwitchButton];
[cell setTarget:self];
[cell setAction:@selector(checkboxChanged:)];
[cell setTitle:@""];
return cell;
}
return nil;
}
现在它完美无缺。