delphi587 포인터 안전하게 다루기 (Pointer & Memory Handling) 포인터 안전하게 다루기 (Pointer & Memory Handling)포인터(Pointer)는 메모리 주소를 직접 다루는 강력한 기능이지만, 잘못 쓰면 프로그램이 즉시 크래시합니다. @, ^ 연산자를 통해 메모리 접근이 가능하며, GetMem/FreeMem으로 수동 관리할 수 있습니다. 포인터보다 레코드, 배열, 객체를 우선 사용하되, 파일 입출력, 네트워크 송수신, DLL 연동 시 포인터가 꼭 필요합니다. program PointerDemo; {$APPTYPE CONSOLE} uses System.SysUtils; type PInt = ^Integer; var Ptr: PInt; begin New(Ptr); // 메모리 할당 try Ptr^ := 12.. 2025. 10. 16. 레코드(Record)로 데이터 구조 최적화하기 레코드(Record)로 데이터 구조 최적화하기 record는 클래스보다 가벼운 구조체형 데이터 컨테이너로, 스택(Stack)에 저장되어 빠르고 메모리 효율적입니다. 단순 데이터 그룹을 표현할 때 적합. packed record를 사용하면 메모리 정렬 패딩을 제거해 파일 입출력 시 크기를 최소화할 수 있습니다. program RecordDemo; {$APPTYPE CONSOLE} uses System.SysUtils; type TEmployee = record EmpNo: Integer; Name: string[30]; Salary: Currency; JoinDate: TDateTime; function GetInfo: string; end; TPack.. 2025. 10. 15. 동적 배열로 유연한 데이터 처리하기 동적 배열로 유연한 데이터 처리하기 고정 배열은 크기가 컴파일 시점에 결정되지만, **동적 배열(Dynamic Array)**은 런타임에서 크기를 조정할 수 있음. ERP/SI 시스템에서 사용자 입력, 조회 결과 등 크기를 알 수 없는 데이터를 저장할 때 필수적. SetLength로 크기를 변경 가능, 반복문(for-in)으로 가독성 있게 순회 가능. // ✅ Delphi 11+ : 동적 배열 program DynamicArrayDemo; {$APPTYPE CONSOLE} uses System.SysUtils; var Arr: TArray; I: Integer; begin SetLength(Arr, 5); // 배열 크기 지정 for I := 0 to High(Arr) do .. 2025. 10. 2. 안전한 if..else와 case 구문: Nullable 대응 패턴 안전한 if..else와 case 구문: Nullable 대응 패턴 if..else와 case는 분기 제어의 핵심 문법. Delphi 11+에서는 Nullable로 DB NULL 값도 안전하게 처리. 레거시(Delphi 7/XE)는 VarIsNull/Assigned 활용. ERP/SI 환경에서 DB 값이 비어 있을 때 예외 방지 및 안정적 분기 처리. // ✅ Delphi 11+ : Nullable와 case 결합 program NullableDemo; {$APPTYPE CONSOLE} uses System.SysUtils, System.Generics.Defaults; var Discount: Nullable; begin Discount := Null; // DB에서 값 없음 if no.. 2025. 9. 30. 리소스 문자열(ResourceString)로 다국어 지원 구현하기 리소스 문자열(ResourceString)로 다국어 지원 구현하기 다국어 지원(i18n)을 고려할 때 ResourceString을 사용하면 코드 수정 없이 번역 리소스만 교체하여 손쉽게 언어를 변경할 수 있습니다. resourcestring SWelcome = '환영합니다!'; SExitMsg = '프로그램을 종료하시겠습니까?'; procedure TForm1.FormCreate(Sender: TObject); begin Caption := SWelcome; end; procedure TForm1.Button1Click(Sender: TObject); begin if MessageDlg(SExitMsg, mtConfirmation, [mbYes, mbNo], 0) = mrYes then .. 2025. 9. 26. TCriticalSection으로 멀티스레드 동기화하기 (Advanced) TCriticalSection으로 멀티스레드 동기화하기 (Advanced) 델파이(Delphi)에서 멀티스레드를 활용하면 성능을 높일 수 있지만, 동시에 여러 스레드가 같은 리소스를 접근하면 데이터 충돌이나 불안정한 동작이 발생할 수 있습니다. 이를 방지하기 위해 TCriticalSection을 사용하면 특정 코드 블록을 한 번에 하나의 스레드만 실행하도록 보호할 수 있습니다. uses System.SysUtils, System.Classes; var Counter: Integer; procedure Worker; var I: Integer; begin for I := 1 to 1000000 do Inc(Counter); // 여러 스레드가 동시에 접근 → 잘못된 값 발생 가.. 2025. 9. 25. Generics.Collections로 타입 안전한 리스트 사용하기 (Beginner) Generics.Collections로 타입 안전한 리스트 사용하기 (Beginner) 델파이(Delphi)에서는 TList 같은 일반 리스트가 있지만, 모든 데이터를 Pointer로 다루어 타입 변환 과정에서 실수할 위험이 있습니다. Generics.Collections의 TList를 사용하면 타입 안전성과 가독성을 높일 수 있습니다. uses System.Generics.Collections, System.SysUtils; procedure Demo; var Numbers: TList; I: Integer; begin Numbers := TList.Create; try Numbers.Add(10); Numbers.Add(20); Numbers.Add(30);.. 2025. 9. 24. DateUtils의 IncDay/IncMonth로 날짜 계산하기 DateUtils의 IncDay/IncMonth로 날짜 계산하기 업무 프로그램에서는 특정 날짜에 일수를 더하거나, 한 달 뒤 날짜를 계산해야 하는 경우가 많습니다. 이때 DateUtils 유닛의 IncDay, IncMonth, IncYear 함수를 사용하면 간단하게 처리할 수 있습니다. uses DateUtils; procedure TForm1.Button1Click(Sender: TObject); var Today, NextWeek, NextMonth: TDate; begin Today := Date; NextWeek := IncDay(Today, 7); // 오늘로부터 7일 뒤 NextMonth := IncMonth(Today, 1); // 오늘로부터 1개월 뒤 S.. 2025. 9. 22. 인터페이스(Interface) 활용하기 (Advanced) 인터페이스(Interface) 활용하기 (Advanced)델파이(Delphi)에서 interface는 다형성과 의존성 분리를 구현하는 핵심 도구입니다. 대규모 프로젝트나 플러그인 구조를 설계할 때 클래스 간 결합도를 낮추고 유지보수성을 높이는 데 큰 도움이 됩니다. uses System.SysUtils; type // 인터페이스 정의 IGreeter = interface ['{7E95F0B8-5F43-4C5A-A8D9-13B8E8F8C2D7}'] procedure SayHello(const Name: string); end; // 구현 클래스 TConsoleGreeter = class(TInterfacedObject, IGreeter) public pr.. 2025. 9. 19. for..in 반복문으로 컬렉션 다루기 (Beginner) for..in 반복문으로 컬렉션 다루기 (Beginner) 델파이(Delphi)에서 배열이나 제네릭 컬렉션을 다룰 때, 전통적인 for i := 0 to ... 문보다 for..in 반복문을 쓰면 코드가 간결하고 읽기 쉬워집니다. 특히 TList나 TDictionary 같은 제네릭 타입에서 활용도가 높습니다. uses System.SysUtils; procedure DemoArray; var Names: array of string; Name: string; begin Names := ['Alice', 'Bob', 'Charlie']; for Name in Names do Writeln('Hello, ' + Name); end; begin DemoArray; end. .. 2025. 9. 18. with 구문 사용의 장단점 (Intermediate) with 구문 사용의 장단점 (Intermediate) 델파이(Delphi)에서는 with 구문을 이용해 특정 객체의 속성이나 메서드를 간결하게 호출할 수 있습니다. 그러나 잘못 사용하면 코드 가독성과 유지보수성에 악영향을 줄 수 있습니다. 언제 with를 쓰고, 언제 피해야 하는지 이해하는 것이 중요합니다. uses Vcl.Forms, Vcl.StdCtrls; procedure TForm1.FormCreate(Sender: TObject); var Btn: TButton; begin Btn := TButton.Create(Self); with Btn do begin Parent := Self; Caption := '클릭하세요'; Left := 50; .. 2025. 9. 16. TStringList를 이용한 Key-Value 데이터 관리 TStringList를 이용한 Key-Value 데이터 관리간단한 설정값이나 임시 데이터를 관리할 때 TStringList의 NameValueSeparator와 Values 속성을 사용하면 효율적으로 Key-Value 형태 데이터를 다룰 수 있습니다. procedure TForm1.Button1Click(Sender: TObject); var SL: TStringList; begin SL := TStringList.Create; try SL.NameValueSeparator := '='; SL.Values['Server'] := '127.0.0.1'; SL.Values['Port'] := '1433'; SL.Values['User'] := 'admin'; .. 2025. 9. 15. TParallel.For로 루프 병렬화하여 멀티코어 성능 끌어올리기 (Advanced) TParallel.For로 루프 병렬화하여 멀티코어 성능 끌어올리기 (Advanced) CPU 연산이 많은 루프를 그대로 돌리면 코어가 여러 개 있어도 한 코어만 쓰는 경우가 많습니다. System.Threading의 TParallel.For를 사용하면 동일한 루프를 자동으로 작업 분할해 여러 코어에서 동시에 처리하므로 실행 시간이 크게 단축될 수 있습니다. uses System.SysUtils, System.Threading, System.SyncObjs, System.Diagnostics; procedure ParallelSumDemo; const N = 5_000_000; var Data: TArray; I: Integer; Total: Int64; SW: TStopwa.. 2025. 9. 11. Record Helpers로 코드 가독성 높이기 (Intermediate) Record Helpers로 코드 가독성 높이기 (Intermediate) 델파이(Delphi)에서 record는 가벼운 데이터 구조체로 자주 사용됩니다. 하지만 기능이 제한적일 수 있습니다. record helper를 사용하면 기존 record에 메서드나 속성을 확장해 넣을 수 있어, 코드의 가독성과 재사용성을 크게 향상시킬 수 있습니다. uses System.SysUtils; type TPoint = record X, Y: Integer; end; // Record Helper 선언 TPointHelper = record helper for TPoint function ToString: string; function DistanceTo(const P: TP.. 2025. 9. 10. TStringList 활용하기 (Intermediate) TStringList 활용하기 (Intermediate)델파이(Delphi)에서 텍스트 데이터를 다룰 때 가장 많이 쓰이는 클래스 중 하나가 TStringList입니다. 파일에서 문자열을 읽고 쓰거나, 키-값 쌍을 관리하거나, 정렬과 검색까지 간단하게 처리할 수 있습니다. uses System.SysUtils, System.Classes; procedure TestStringList; var SL: TStringList; begin SL := TStringList.Create; try // 문자열 추가 SL.Add('Apple'); SL.Add('Banana'); SL.Add('Cherry'); // 특정 인덱스 접근 Writeln('첫 번째.. 2025. 9. 9. TFDQuery.FieldByName 성능 최적화하기 TFDQuery.FieldByName 성능 최적화하기반복 루프 안에서 FieldByName을 직접 호출하면 성능 저하가 발생할 수 있습니다. 필드 객체를 캐싱해두면 처리 속도를 크게 개선할 수 있습니다. procedure OptimizeFieldAccess(Qry: TFDQuery); var FName, FEmail: TField; begin Qry.SQL.Text := 'SELECT Name, Email FROM Customers'; Qry.Open; // 필드 캐싱 FName := Qry.FieldByName('Name'); FEmail := Qry.FieldByName('Email'); while not Qry.Eof do begin // 반복 루프에서 직접 .. 2025. 9. 8. TMonitor를 이용한 객체 동기화 (Advanced) TMonitor를 이용한 객체 동기화 (Advanced)멀티스레드 환경에서 여러 스레드가 동일한 객체에 접근할 경우, 동기화가 필요합니다. TCriticalSection은 프로세스 내 자원 보호에 유용하지만, 델파이(Delphi)에서는 TMonitor라는 더 현대적이고 객체 지향적인 동기화 방법을 제공합니다. TMonitor는 객체 자체에 대한 잠금(lock)을 제공하며, Wait, Pulse, PulseAll을 통해 스레드 간 조건 동기화도 가능하게 합니다. uses System.SysUtils, System.Classes; type TSharedBuffer = class private FData: string; public procedure WriteData(.. 2025. 9. 5. TCriticalSection으로 멀티스레드에서 자원 보호하기 (Intermediate) TCriticalSection으로 멀티스레드에서 자원 보호하기 (Intermediate)델파이(Delphi)에서 멀티스레드 프로그램을 작성할 때, 여러 스레드가 동시에 같은 변수나 객체를 수정하면 Race Condition(경쟁 상태) 이 발생할 수 있습니다. 이런 문제를 막으려면 스레드 간에 공유되는 자원 접근을 동기화해야 합니다. TCriticalSection은 간단하게 임계 구역(critical section)을 설정하여 한 번에 한 스레드만 진입하도록 보장합니다. uses System.Classes, System.SyncObjs, System.SysUtils; var Counter: Integer = 0; CS: TCriticalSection; procedure Incremen.. 2025. 9. 4. TStringGrid에서 행 전체 복사/붙여넣기 기능 구현하기 TStringGrid에서 행 전체 복사/붙여넣기 기능 구현하기 업무용 그리드 화면에서 사용자가 행 전체를 복사/붙여넣기 할 수 있으면 데이터 입력 효율성이 크게 올라갑니다. uses Vcl.Clipbrd; procedure CopyRowToClipboard(Grid: TStringGrid; ARow: Integer); var Col: Integer; Line: string; begin Line := ''; for Col := 0 to Grid.ColCount - 1 do begin Line := Line + Grid.Cells[Col, ARow]; if Col Line := Line + #9; // 탭 구분자 end; Clipboard.AsText .. 2025. 9. 3. 루프에서 문자열 결합은 TStringBuilder로 최적화하기 (Intermediate) 루프에서 문자열 결합은 TStringBuilder로 최적화하기 (Intermediate)루프에서 S := S + ...로 문자열을 이어 붙이면 매번 새 버퍼가 생성되어 메모리 재할당과 복사가 반복됩니다. TStringBuilder는 내부 버퍼를 확장해가며 추가하기 때문에 할당/복사 횟수를 크게 줄여 대용량 처리에서 유리합니다. 초기 용량(Capacity)을 넉넉히 잡으면 더 빨라집니다. program StringBuilderDemo; {$APPTYPE CONSOLE} uses System.SysUtils, System.Diagnostics; function BuildWithPlus(Count: Integer): string; var i: Integer; S: string; begin .. 2025. 9. 3. 이전 1 2 3 4 ··· 30 다음