小编Mar*_*ski的帖子

SQLite中的主键是否需要索引?

当一个整数列在SQLite表中被标记为主键时,是否应该为它显式创建索引?SQLite似乎不会自动为主键列创建索引,但考虑到其目的,它可能无论如何都要对其进行索引?(我会一直在搜索那个专栏).

对于字符串主键,情况会有所不同吗?

sqlite indexing primary-key

124
推荐指数
3
解决办法
3万
查看次数

找出注册全球热键的流程?(Windows API)

据我所知,Windows没有提供API函数来告诉应用程序注册了一个全局热键(通过RegisterHotkey).我只能发现如果RegisterHotkey返回false,则注册了热键,但不是"拥有"热键的人.

在没有直接API的情况下,是否会有迂回的方式?Windows维护与每个注册热键相关联的句柄 - 这有点令人抓狂,因此无法获取此信息.

可能不起作用的示例:发送(模拟)已注册的热键,然后拦截Windows将发送给注册它的进程的热键消息.首先,我不认为拦截消息会显示目标窗口句柄.其次,即使有可能,这也是一件坏事,因为发送热键会触发各种程序中各种可能不需要的活动.

这并不重要,但我已经看到了对这种功能的频繁请求,并且我自己也是注册热键的应用程序的受害者,甚至没有在UI或文档中的任何地方公开它.

(在Delphi工作,只不过是WinAPI的学徒,请善待.)

delphi api winapi hotkeys registerhotkey

105
推荐指数
3
解决办法
3万
查看次数

当另一个表中不存在匹配项时,从SQLite表中删除行

我需要删除SQLite表中的行,其中行ID在另一个表中不存在.SELECT语句返回正确的行:

SELECT * FROM cache LEFT JOIN main ON cache.id=main.id WHERE main.id IS NULL;
Run Code Online (Sandbox Code Playgroud)

但是,delete语句会从SQLIte生成错误:

DELETE FROM cache LEFT JOIN main ON cache.id=main.id WHERE main.id IS NULL;
Run Code Online (Sandbox Code Playgroud)

错误是:SQLite错误1 - 接近"左":语法错误.我可以使用另一种语法吗?

sqlite left-join sql-delete

23
推荐指数
2
解决办法
2万
查看次数

在Delphi中以线程安全的方式增加和返回一个整数

在单线程应用程序中,我使用如下代码:

Interface
    function GetNextUID : integer;
Implementation
    function GetNextUID : integer;
    const
      cUID : integer = 0;
    begin
      inc( cUID );
      result := cUID;
    end;
Run Code Online (Sandbox Code Playgroud)

这当然可以作为单个对象实现,等等 - 我只是给出了最简单的例子.

问:如何修改此函数(或设计类)以从并发线程安全地实现相同的结果?

delphi multithreading increment thread-safety

14
推荐指数
3
解决办法
6430
查看次数

在Delphi XE中"保持最佳"主窗体和模态对话框

在Delphi XE Update 1中,如果父(主)表单的FormStyle设置为fsStayOnTop,我会看似模态表单的随机行为.

1)使用MainFormOnTaskbar:= False(旧方式),一切都"正常".使用新的MainFormOnTaskbar:= True,当主窗体设置为"保持在最顶层"时,模态窗体隐藏在主窗体后面.在大多数情况下说

modalForm.PopupParent := self;
Run Code Online (Sandbox Code Playgroud)

就在调用modalForm.ShowModal之前似乎有所帮助.但不总是.

2)我所有的模态形式都很简单,没有多余的装饰,定位在MainFormCenter,没有使用表单继承等.然而PopupParent修复仅适用于大约一半,而另一半仍然隐藏在主窗体后面.最奇怪的是,在一种情况下,不相关的代码行的排序会破坏或产生它.请参阅此代码中标记为(1)和(2)的行:

procedure TEchoMainForm.DBMaintenancePrompt( actions : TMaintenanceActions );
var
  frm : TDBMaintenanceForm;
begin
  frm := TDBMaintenanceForm.Create( self );
  try
    frm.Actions := actions; // (1)
    frm.PopupParent := self; // (2)
    frm.ShowModal;
  finally
    frm.Free;
  end;
end;
Run Code Online (Sandbox Code Playgroud)

按此顺序执行时,模态窗体正确显示在主窗体的顶部.但当我扭转线条时,模态形式隐藏在主线之后.标记为(1)的行设置模态形式的属性,这导致在TRzCheckGroup中未选中的多个复选框被检查,坐在TRzPageControl(来自Raize组件)上.这是上面第(1)行执行时运行的setter方法:

procedure TDBMaintenanceForm.SetActions(const Value: TMaintenanceActions);
var
  ma : TMaintenanceAction;
begin
  for ma := low( ma ) to high( ma ) do
    cgMaintActions.ItemChecked[ ord( ma )] := ( …
Run Code Online (Sandbox Code Playgroud)

delphi modal-dialog stayontop

10
推荐指数
1
解决办法
2232
查看次数

Delphi线程等待数据,处理它,然后继续等待

我需要在Delphi中创建一个具有以下特征的线程:

  • 等待主线程将数据添加到共享队列.
  • 处理队列中的所有数据,将结果返回给主线程(对于最后一部分,我只是将消息发送到主窗口).处理非常耗时,因此当工作线程处理先前的条目时,可以将新数据添加到队列中.
  • 使用尽可能少的cpu周期继续等待.

我无法向线程发送消息,因为它没有窗口句柄.

我应该使用WaitForObject的某些变体吗?如果是这样,等待的是什么?如果没有,那么我如何保持线程等待,然后在新数据进入队列时唤醒它?

我读过Multithreading - Delphi Way,它似乎没有回答我的问题.也许 OmniThreadLibrary可以做我需要的事情; 我无法分辨,因为文档很少.我不太了解一般的线程,以确定库是否会在这里提供帮助以及如何使用它(甚至为什么要使用它而不是仅使用TThread后代).

delphi queue resume multithreading suspend

9
推荐指数
1
解决办法
9041
查看次数

SetWindowsHookEx创建一个本地钩子.如何使其全球化?

在Delphi XE应用程序中,我正在尝试设置一个全局挂钩来监视焦点更改.钩子是在一个DLL中创建的:

focusHook := SetWindowsHookEx( WH_CBT, @FocusHookProc, HInstance, 0 );
// dwThreadId (the last argument) set to 0 should create a global hook
Run Code Online (Sandbox Code Playgroud)

在同一个DLL中,我有一个将消息发布到主机应用程序窗口的钩子过程:

function FocusHookProc( code : integer; wParam: WPARAM; lParam: LPARAM ) : LResult; stdcall;
begin
  if ( code < 0 ) then
  begin
    result := CallNextHookEx( focusHook, code, wParam, lParam );
    exit;
  end;

  result := 0;

  if ( code = HCBT_SETFOCUS ) then
  begin
    if ( hostHWND <> INVALID_HANDLE_VALUE ) then
      PostMessage( hostHWND, cFOCUSMSGID, wParam, lParam ); …
Run Code Online (Sandbox Code Playgroud)

delphi hook winapi setwindowshookex

9
推荐指数
1
解决办法
7142
查看次数

在SQLite数据库中存储日期时间值的最佳方法(Delphi)

我将日期时间值存储在SQLite数据库中(使用Delphi和DISqlite库).数据库的性质使得它永远不需要在计算机或系统之间传输,因此互操作性不是约束.我的重点是阅读速度.datetime字段将被编入索引,我将对其进行大量搜索,并按顺序读取数千个日期时间值.

由于SQLite没有datetime值的显式数据类型,因此有以下几种选择:

  • 使用REAL数据类型并直接存储Delphi的TDateTime值:最快,加载时不从字符串转换; 无法使用数据库管理器(如SQLiteSpy)调试日期,因为日期不会是人类可读的.不能使用SQLite日期函数(?)

  • 使用简单的字符串格式,例如YYYYMMDDHHNNSS:需要转换但在CPU上相对容易(不需要扫描分隔符),数据是人类可读的.仍然不能使用SQLite日期函数.

  • 做点别的.推荐的做法是什么?

我已经阅读了http://www.sqlite.org/lang_datefunc.html但是没有提到要使用的数据类型,并且没有在编程中正式学习,我不太关注朱利安日期.为什么要额外转换?我会仔细阅读这些值,因此字符串和TDateTime之间的任何额外转换都会增加成本.

delphi sqlite format datetime

8
推荐指数
2
解决办法
8264
查看次数

在SQLite中连接三个表的最佳方法

互联网书签的(简化)数据库.我认为以逻辑方式组织表是有意义的,如下所示:

Bookmarks (id, title, url; basically external data)
+------+------------+-----+
| suid |   Title    | ... |
+------+------------+-----+

User (user-specific data: favorites, ratings, etc)
+------+------------+-----+
| suid | IsFavorite | ... |
+      +  (0 or 1)  +     +
+------+------------+-----+

History (last used, use count etc)
+------+------------+-----+
| suid |  LastUsed  | ... |
+      +(TDateTime) +     +
+------+------------+-----+
Run Code Online (Sandbox Code Playgroud)

('suid'是唯一ID,整数主键)

从标记为收藏的书签我需要选择最近使用的 N (为方便起见,在运行时填充菜单).

SELECT Bookmarks.suid, Title from Bookmarks
    INNER JOIN User USING (suid)
    INNER JOIN History USING (suid) …
Run Code Online (Sandbox Code Playgroud)

sql sqlite greatest-n-per-group

8
推荐指数
1
解决办法
1万
查看次数

在Delphi中控制应用程序音量

我甚至不确定这是否适合一个问题,但这只是一个问题.我有一个用Delphi XE编写的互联网广播播放器,使用BASS库进行音频流和播放.该应用程序需要在Windows XP,Vista和7下运行.

Bass可以轻松控制全局音量,但无法使声音静音,一般来说,根据每个应用程序控制音量更好.

Bass还可以轻松控制"通道"(流)的音量,但同样没有静音,这也不是适合每个应用程序的控制.(Windows混音器中的应用程序音量控制不受影响.)

据我所知,对于Vista及以上版本,我需要ISimpleAudioVolume和/或IAudioEndpointVolume,但找不到这些的Delphi实现.所以问题的一部分是,它作为第三方库存在吗?

第二部分是什么是在XP上控制音量和切换静音(系统范围或每个应用程序)的正确方法,这些接口不可用?

delphi audio volume windows-vista

8
推荐指数
1
解决办法
2540
查看次数