Ugly code of the day :
Ugly code of the day :
class function TFile.DoReadAllBytes(const Path: string): TBytes;
var
LFileStream: TFileStream;
begin
LFileStream := nil;
try
LFileStream := OpenRead(Path);
SetLength(Result, LFileStream.Size);
LFileStream.ReadBuffer(Pointer(Result)^, Length(Result));
finally
LFileStream.Free;
end;
end;
class function TFile.DoReadAllBytes(const Path: string): TBytes;
var
LFileStream: TFileStream;
begin
LFileStream := nil;
try
LFileStream := OpenRead(Path);
SetLength(Result, LFileStream.Size);
LFileStream.ReadBuffer(Pointer(Result)^, Length(Result));
finally
LFileStream.Free;
end;
end;
I have a 25Gb large file I'd like to try that on...
ReplyDeleteNick Hodges was already clogging up my feed =P
ReplyDeleteFrédéric Hannes That was a pre-empting attempt ;-)
ReplyDelete:D
ReplyDeleteEric Grange oh my goodness... Lars Fosdal LOL*2!
ReplyDeleteInteresting. I am also using a prefix of "L" for local variables (starting with lower case, upper case now...) since years. Seems to be a more and more used coding style?!
ReplyDeleteNo L for me, but a leading a in aName for arguments.
ReplyDeleteIndexes: ix, jx, kx, or any ?x ...
Graeme Geldenhuys but we didn't work at the same company? ;-)
ReplyDeleteI only prefix class fields with F. In the past I've aways used lowercase for short variable names, but I recently moved to using caps and longer variable names, like "Idx" instead of "i". Resulting in my average array loop looking like:
ReplyDeleteLen := Length(Arr);
for Idx := 0 to Len - 1 do
Do you use properties even for simple field access?
ReplyDeleteI tend to wrap them in a property
MyField:Type read FMyField write FMyField;
and really wish I could explicitly disable direct references to FMyField elsewhere in the same class.
Lars Fosdal
ReplyDeleteI do. Sometimes I even do implement private properties :D It's always easier to change if you do need to add a property setter later.
Why not implement private properties if it results to clean code ?
ReplyDeletee.g.
type
TFoo = class
....
private {or strict private }
function GetBar: TBar;
procedure SetBar (const Value: TBar);
property Bar: TBar read GetBar write SetBar;
end;
where GetBar is
Result := someDataSource.DataSet.FieldByName('Bar').As....
and SetBar is
someDataSource.DataSet.FieldByName('Bar').As.... := Value;
in case of first stage of legacy code refactoring it really helps
The coding style that works well for us
ReplyDelete1. Give local variables as short names as possible. A typical variable name is 2 symbols length. For this function it will be fs instead of LFileStream.
Why: The code is much more readable and easier to debug. Just try it, it works! A function has a narrow scope, and variables are most often self documented by the type and by the code. The trick is also to name similar variables in different functions similar way. E.g. we use e for Edge, p for point, p for previous, c for current, n for next, so cp: T3DPoint means CurrentPoint, ne: TEdge means NextEdge;
2. Give fields the "f" prefix, nothing new here.
Why: This way you distinguish fields from local variables. No need for the L.
3. Always add self. before internal method calls and internal properties access.
Why: Properties may have side effects, so by prefixing them with self. you emphasize this.
By prefixing own methods with self. you distinquish them from global functions. Methods usually operate on object fields, adding self. just makes it clear for a reader.
Apart from counters I never use short names, unless it is object references, and then it's usually org, cpy, nxt, prv, first or last. Reading Code Complete cured my short name delusion.
ReplyDeleteUsing self - occasionally, but do you fully qualify library functions too?
ReplyDeleteLars Fosdal I qualify global functions sometimes, when I want the Ctrl+[space] showed me the variants. For the methods, if a method operates on object fields using self is mandatory, if it doesn't, than self is optional depending on whether it improves readability or not.
ReplyDeleteLars Fosdal I never expose class fields, so even for simple ones I use properties as public members, but I usually don't use properties in private or protected.
ReplyDeleteSomething that followed me from Python back to Delphi is, explicit is better than implicit. I try to always use self, but have not completely followed through with unit names.
ReplyDelete