我有以下要求:我應該如何在Perl中實現原子序列?
- 序列是唯一的主機(沒有共享遞增是必要的)
- 序列必須單調增加。
- 序列必須在進程間保持不變。
- 在多個進程同時運行的情況下,遞增序列必須是原子的。
- 大部分時間文件將被更新,並在更新後讀取新值。但是,也應該可以在不更新的情況下讀取當前值。
我可以一起破解perl代碼,這將大致做到這一點,但我想要一個更優雅的解決方案。
我有以下要求:我應該如何在Perl中實現原子序列?
我可以一起破解perl代碼,這將大致做到這一點,但我想要一個更優雅的解決方案。
存放在文件中的序列號和使用flock
,以確保只有一個進程可以訪問它:
sub set { # seed the sequence number file
my ($file, $number) = @_;
open my $fh, '>', $file;
print $fh $number;
} # implicit close
sub get {
my $file = shift;
my $incr = @_ ? shift : 1; # get($f) is like get($f,1)
open my $lock, '>>', "$file.lock";
flock $lock, 2;
open my $fh, '<', $file;
my $seq = <$fh>;
close $fh;
set($file, $seq+$incr) if $incr; # update sequence number
close $lock;
return $seq;
}
你可以叫這個爲get($file,0)
檢索序列號不改變它。
系統時間提供單調增加的順序,地址(2):
perl -MTime::HiRes=time -lwe "print time"
直到有人重置時鐘...
持久性(3)和incrementations的原子性(4)似乎需要一個鎖定數據庫。伯克利DB想到了。但是你可能正在尋找更簡單的東西,除非你已經在使用它了。沒有更新(5)的閱讀將是沒有問題的。單調增加的序列(2)也不會。
我不確定你的意思是「對主機唯一」和「共享增量」(1)。如果來自不同主機的序列元素具有相同的值,那麼您可以將該方法乘以所有服務器。否則,您只能通過網絡訪問其他人必須訪問的一個序列。
我一起黑客一起perl代碼,大致這樣做。將當前序列號存儲在文件中並在「flock」包裝器中訪問/更新它是否優雅? – mob 2011-06-09 19:54:13
如果我不必親自編寫代碼,那麼它的確如此:) – 2011-06-09 20:27:34