我想创建轻量级对象数据包,以便在客户端和服务器应用程序之间传递。
这是一项非常简单的任务,我只能控制1个字节,所以 一个字节中的每个位都有不同的含义,
仅使用位
0 = False
1 = True
现在我需要:
1 - Loaded from database
2 - Persisted
3 - Changed
4 - Marked to Delete
5 -
6 -
7 - Null Value
8 - Read Only
1) How do I use bit operators in Delphi to check each bit value?
2) How do I set the bit Values?
解决方案
在所有帮助之后,我会使用下一个Set
TStateType = (
stLoaded = 0, // loaded from persistance
stNative = 2, // value loaded and converted to native type
stPersisted = 3, // saved
stChanged = 4, // object or member changed
stToDelete = 5, // marked to delete
stReadOnly = 6, // read only object, will not allow changes
stNull = 7 // value is null
);
TState = Set of TStateType;
对于流 - >坚持,这将是使用的记录:
TDataPackage = record
Data: TBytes;
TypeInfo: TMetaInfo;
State: Byte;
Instance: TBuffer;
end;
谢谢伙伴们,获取所有答案和评论。
答案 0 :(得分:7)
我真的使用了一套。但是,我看到你真的想要一个字节。在任何地方使用集合,然后在最后将类型转换为一个字节。
这个解决方案需要更少的输入,支持标准的delphi运算符,并且实际上没有性能损失,正如Barry Kelly指出的那样。
procedure Test;
type
TSetValues = (
TSetValue1 = 0,
TSetValue2 = 1,
TSetValue4 = 2,
TSetValue8 = 3,
TSetValue16 = 4,
TSetValue32 = 5,
TSetValue64 = 6,
TSetValue128 = 7
);
TMySet = set of TSetValues;
var
myValue: byte;
mySet: TMySet;
begin
mySet := [TSetValue2, TSetValue16, TSetValue128];
myValue := byte(mySet);
ShowMessage(IntToStr(myValue)); // <-- shows 146
end;
答案 1 :(得分:6)
我会使用一套:
type
TMyDatum = (mdLoaded, mdPersisted, mdChanged, mdMarkedToDelete, ...);
TMyData = set of TMyDatum;
var
Foo: TMyData;
begin
Foo := [mdLoaded, mdChanged];
if (mdPersisted in Foo) then ...
这些是作为整数实现的,因此您可以轻松地传递它们。我发现代码比按位运算符更容易阅读。
答案 2 :(得分:1)
This page描述了Delphi运算符,包括按位运算符。
听起来你需要使用和运算符。例如:
const
LOADED_FROM_DATABASE = 1;
PERSISTED = 2;
CHANGED = 4;
// etc...
//...
if (bitFlags and LOADED_FROM_DATABASE) <> 0 then
begin
// handle LOADED FROM DATABASE
end;
if (bitFlags and PERSISTED) <> 0 then
begin
// handle PERSISTED
end;
// etc...
为了设置标志,您可以使用OR:
bitFlags := LOADED_FROM_DATABASE or PERSISTED or CHANGED;