首页 > 程序设计

Lua table转json (Delphi实现)

Lua的table真是无敌了,无比的强大。写了一个函数,将table转为宿主程序的JSON对象,用了qjson。

function ParseTable: TQJson;
var
  KeyType, ValueType: Integer;
  Key, Value: string;
  KeyIndex: Integer;
begin
  Result := TQJson.Create;
  if lua_istable(FLuaState, -1) then
  begin
    lua_pushnil(FLuaState);

    while lua_next(FLuaState, -2) > 0 do
    begin
      KeyType := lua_type(FLuaState, -2);
      ValueType := lua_type(FLuaState, -1);

      if ValueType = LUA_TTABLE then
      begin
        if KeyType = LUA_TNUMBER then //Key为数字,意为数组
        begin
          KeyIndex := lua_tointeger(FLuaState, -2);
          if Result.IsArray then
            Result.Add(ParseTable)
          else
            Result.ToArray.Add(ParseTable);
        end
        else begin
          Key := lua_tostring(FLuaState, -2);
          Result.Add(Key, ParseTable);
        end;
      end
      else begin
        if KeyType = LUA_TNUMBER then //Key为数字,意为数组
        begin
          KeyIndex := lua_tointeger(FLuaState, -2);
          Value := lua_tostring(FLuaState, -1);

          if Result.IsArray then
            Result.Add.AsString := Value
          else
            Result.ToArray.Add.AsString := Value;
        end
        else begin
          Key := lua_tostring(FLuaState, -2);
          Value := lua_tostring(FLuaState, -1);

          Result.Add(Key).AsString := Value;
        end;
      end;

      lua_pop(FLuaState, 1);
    end;
  end;
end;

注:FLuaState为lua_state。

使用方法:

把需要使用的table压入栈顶,然后调用该函数即可。

lua_getglobal(FLuaState, 't');
json := ParseTable(FLuaState);

 

2016-7-25 22:28:41 评论(1) 程序设计
全文完 阅读全文

Laravel5 nginx urlrewrite设置

搞了好几天Laravel,$_GET一直取不出值,才怀疑是不是nginx的urlrewrite配错了。

我之前写的配置是 try_files $uri $uri/ /index.php?$1;

经测试应该为 try_files $uri $uri/ /index.php?$query_string;

正确的设置如下:

server {
    listen       80;
    server_name  域名;
    root         x:/目录/public;

    location / {
        index    index.php index.htm index.html;
        try_files $uri $uri/ /index.php?$query_string;
        #try_files $uri $uri/ /index.php?$1;
    }

    location ~ \.php$ {
        fastcgi_pass   127.0.0.1:9000;
        fastcgi_index  index.php;
        fastcgi_param  SCRIPT_FILENAME  $document_root/$fastcgi_script_name;
        include        fastcgi_params;
    }

    location ~ /\.ht {
        deny  all;
    }
}

2016-4-27 01:20:53 评论(0) 程序设计
全文完 阅读全文

Delphi Android开发放置了TFDGUIxWaitCursor仍然报错的问题

利用Delphi开发Android程序,使用SQLite数据库,在DataModule下放置了TFDGUIxWaitCursor仍然报错,

Object factory for class {3E9B315B-F456-4175-A864-B2573C4A2201}, provider [Forms], is missing. To register it, you can drop component [TFDGUIxWaitCursor] into your project

需要将TFDGUIxWaitCursor控件的Provider属性改为FMX才行。

2016-4-13 08:55:09 评论(0) 程序设计
全文完 阅读全文

Delphi在Android下无法调试的问题

最新的Delphi 10 Seattle在Android下调试老是报错,

Unable to start gdbserver on port '64311'
Can't open socket: Permission denied..

没有权限的问题,用Root Explorer给 /data/data/包名 赋上777权限即可。

2016-4-13 08:40:13 评论(0) 程序设计
全文完 阅读全文

eclipse选择指定版本的JDK

64位WIN10系统中安装了64位的JDK,配置好了JAVA_HOME。之后安装了Aptana(eclipse的一个修改版本)。Aptana只有32位的,死活打不开,提示

Failed to load the JNI shared library "C:\Program Files\Java\jdk1.8.0_74\bin\..\jre\bin\server\jvm.dll".

查了资料,是由于JAVA_HOME定义的JDK是64位的,而Aptana是32位的,因此无法使用。

eclipse可以指定你需要使用的JDK版本,在安装目录下修改eclipse.ini(当然Aptana要个性AptanaStudio3.ini),在 -vmargs 之前增加两行:

-vm
c:\Program Files (x86)\Java\jdk1.7.0_55\bin

将路径替换成指定JDK的目录,注意后面有个bin。正常打开。

 

2016-3-21 17:39:27 评论(0) 程序设计
全文完 阅读全文

MySQL 1067错误

刚才在Win10里安装MySQL5.7,启动服务时报1067错误,查看日志:

2016-02-09T09:25:23.802959Z 0 [ERROR] InnoDB: Operating system error number 87 in a file operation.
2016-02-09T09:25:23.804966Z 0 [Note] InnoDB: Some operating system error numbers are described at http://dev.mysql.com/doc/refman/5.7/en/operating-system-error-codes.html
2016-02-09T09:25:23.808971Z 0 [ERROR] InnoDB: File .\ib_logfile0: 'aio read' returned OS error 187. Cannot continue operation
2016-02-09T09:25:23.811975Z 0 [ERROR] InnoDB: Cannot continue operation.

求助于网上资料,只需要在my.ini的最后添加一行:

innodb_flush_method=normal

问题解决。

2016-2-9 17:30:39 评论(0) 程序设计
全文完 阅读全文

Laravel 5.2 Blade section 学习笔记

这几天在学Laravel,综合官方文档及网上资料,记下一些心得。

Blade的视图文件存放在resources/views目录下,文件名以.blade.php结尾。

定义片断(section):

<body>
    @section('text')
        Hello, World.
    @endsection
    <h1>@yield('text', '默认值')</h1>
</body>

@section的作用是定义一个片断;

@yield的作用是应用片断,第二个参数的作用是设置默认值,当找不到text片断时显示该值,可省略。

以上代码输出:

<body>
    <h1>Hello, World.</h1>
</body>

@endsection还可以变更为@show,意为当程序执行到这一行的时候,立即输出该片断(section)。可放在布局模板中,相当于yield加入了默认值参数。如果在后续代码中找不到该section,则显示section里的默认值。

引入(继承)一个模板:

@extends('模板名')

模板可放在子目录中,引用的时候用点“.”代替目录分隔符。若文件为layout/master.blade.php,引用为@extends('layout.master')。

section可定义多次,用@parent引用父section,但要注意section定义的顺序。php代码是由上往下执行,先定义的section先执行,后定义的section后执行。但最终显示的顺序与此相反,后定义的section为父,先定义的section为子。所以是由先写的section继承后写的section。

<?php
    $a=0;
?>
<body>
    @section('text')
        <h1>Hello, {{$a+=11}}</h1><br />
        @parent
    @endsection
    @section('text')
        <h2>World, {{$a+=33}}</h2><br />
    @endsection
    @yield('text')
</body>

以上代码输出的值为:

<body>
    <h1>Hello, 11</h1><br />
    <h2>World, 44</h2><br />
</body>

可以看到,“Hello”继承了“World”的section,并将“World”的内容插入进来,但是输入的值却是根据程序执行顺序由上到下计算的。
 

2016-1-31 22:20:57 评论(1) 程序设计
全文完 阅读全文

Delphi利用Indy构建SMTP服务器

近日搭邮件服务器,按照网上的教程总出现这样那样的错误。浪费了好几天,不如自己写个算了。

幸好Indy将SMTP协议封装好了,使用起来十分方便。

简述一下邮件投递的过程。连接上SMTP服务器并身份验证后,SMTP服务器检查目标邮箱系统域名的MX记录,再将邮件投递至MX记录所指向的地址。

MX(Mail Exchanger)记录是邮件交换记录,它指向一个邮件服务器,用于电子邮件系统发邮件时根据收信人的地址后缀来定位邮件服务器。

主要用了三个控件,IdSMTPServer负责SMTP服务器的接收投递,IdDNSResolver负责域名解析,IdSMTP负责发送邮件。

取MX记录:

function GetMx(const Domain: string): string;
var
  I: Integer;
  DnsRes: TResultRecord;
  LMx: TMxRecord;
  iPref: Word;
  ServerList: TStrings;
begin
  Result := '';
  IdDNSResolver1.Host := '180.76.76.76'; //设定域名解析服务器
  IdDNSResolver1.QueryType := [qxMX];    //设定需要解析MX记录
  IdDNSResolver1.Resolve(Domain);        //解析域名
  iPref := High(Word);
  ServerList := TStringList.Create;
  for I := 0 to IdDNS.QueryResult.Count - 1 do
  begin
    DnsRes := IdDNS.QueryResult[I];
    if (DnsRes is TMXRecord) then
    begin
      LMx := TMXRecord(DnsRes);
      Result := LMx.ExchangeServer;
      if LMx.Preference < iPref then
      begin
        iPref := LMx.Preference;
        ServerList.Insert(0, LMx.ExchangeServer);
        //可能一个域名有多条MX记录,按照优先级最终取出第一条
      end else begin
        ServerList.Add(LMx.ExchangeServer);
      end;
    end;
  end;
  if ServerList.Count > 0 then
    Result := ServerList[0];
  ServerList.Free;
end;

验证投递邮箱合法性:直接设为rAddressOk跳过

procedure TForm1.IdSMTPServer1RcptTo(ASender: TIdSMTPServerContext;
  const AAddress: string; AParams: TStrings; var VAction: TIdRCPToReply;
  var VForward: string);
begin
  VAction := TIdRCPToReply.rAddressOk;
end;

验证用户:直接将VAuthenticated设为True跳过

procedure TForm1.IdSMTPServer1UserLogin(ASender: TIdSMTPServerContext;
  const AUsername, APassword: string; var VAuthenticated: Boolean);
begin
  VAuthenticated := True;
end;

SMTPServer收到邮件时的处理:

procedure TForm1.IdSMTPServerMsgReceive(ASender: TIdSMTPServerContext;
  AMsg: TStream; var VAction: TIdDataReply);
var
  MailMsg: TIdMessage;
  P: Integer;
  EMail: string;
  Domain: string;
  ThoughAddress: string;
begin
  MailMsg := TIdMessage.Create;
  try
    MailMsg.LoadFromStream(AMsg);
    EMail := MailMsg.Recipients.EMailAddresses; //取目标邮件地址
    P := EMail.IndexOf('@');
    Domain := EMail.Substring(P + 1, EMail.Length); //取邮件域名
    ThoughAddress := GetMx(Domain); //取投递的MX记录

    with IdSMTP1 do //通过IdSMTP发送邮件
    begin
      Host := ThoughAddress;
      Port := 25;
      Connect;
      try
        Send(MailMsg); //转发刚才收到的邮件
      finally
        Disconnect;
      end;
    end;
  finally
    FreeAndNil(MailMsg);
  end;

  VAction := TIdDataReply.dOk;
end;

程序在Delphi XE7 update1 调试通过。

2014-12-20 20:20:03 评论(1) 程序设计
全文完 阅读全文

SQLite字符串连接

SQLite的字符串连接不是用 + 而是用 || 。

+是将前后两字符串转成数字再进行加法运算。

||是将前后两字符串连接。

2014-12-7 14:18:56 评论(1) 程序设计
全文完 阅读全文

Delphi的类变量、类构造方法

type
  TTest = class
  private
    class var A: Integer;  //类变量
    B: Integer; //普通成员变量
  public
    class constructor Create;  //类构造方法
    class destructor Destroy;  //类析构方法
    constructor Create; //实例构造方法
    destructor Destroy; //实例析构方法
  end;

类构造方法顾名思义就是在类初始化的时候执行。以前只能在initialization段中才能初始化,现在可以在类构造方法中初始化类变量,使得程序结构更加有条理。

2014-10-31 10:57:23 评论(0) 程序设计
全文完 阅读全文
1/2, 18 « 12 »