楼主: nyfor

[精华] 最小源代码擂台

[复制链接]
论坛徽章:
5
奥运会纪念徽章:摔跤
日期:2008-07-02 08:48:392009日食纪念
日期:2009-07-22 09:30:00优秀写手
日期:2013-12-18 09:29:11SQL数据库编程大师
日期:2016-01-13 10:30:43SQL大赛参与纪念
日期:2016-01-13 10:32:19
331#
发表于 2008-5-26 09:34 | 只看该作者
CREATE OR REPLACE function SYSTEM.my_add_months(p_date_string varchar2, p_months number) return varchar2 IS
t int:=p_date_string;
l int:=100;
y int:= t/l/l; m int:= mod(t/l,l); d int:= mod(t,l);
BEGIN
   t := case when m=2 and d>=28 then case when not ((mod(y,4)=0 and mod(y,100)!=0 or mod(y,400)=0) and d=28) then 1 end
             when m in(4,6,9,11) and d=30 then 1 when d=31 then 1 end;
   m := m+p_months;
   y := trunc(y+(m-1)/12);
   m := mod(m,12);
   if m<=0 then m:=m+12; end if;
   l:=28;
   if mod(y,4)=0 and (mod(y,100)!=0 or mod(y,400)=0) then l:=29; end if;
   d := case when m in(4,6,9,11) and (d>30 or t=1) then 30
        when m=2 and (d>l or t=1) then l
        when t=1 then 31
        else d end;
   RETURN y||lpad(m,2,'0')||d;
END;
/

SQL> call t();
Congratulation ... Code Length: 555 Bytes. Times: 00:00:03







走hotiice的思路,少4个字节,不过这已经到26号了
CREATE OR REPLACE function SYSTEM.my_add_months(p_date_string varchar2, p_months number) return varchar2 IS
t int:=p_date_string;
l int:=100;
y int:= t/l/l; m int:= mod(t/l,l); d int:= mod(t,l);
BEGIN
   t := case when m=2 and d>=28 then case when not ((mod(y,4)=0 and mod(y,25)!=0 or mod(y,16)=0) and d=28) then 1 end
             when m in(4,6,9,11) and d=30 then 1 when d=31 then 1 end;
   m := m+p_months;
   y := trunc(y+(m-1)/12);
   m := mod(m,12);
   if m<=0 then m:=m+12; end if;
   l:=28;
   if mod(y,4)=0 and (mod(y,25)!=0 or mod(y,16)=0) then l:=29; end if;
   d := case when m in(4,6,9,11) and (d>30 or t=1) then 30
        when m=2 and (d>l or t=1) then l
        when t=1 then 31
        else d end;
   RETURN y||lpad(m,2,'0')||d;
END;
/

SQL> call t();
Congratulation ... Code Length: 551 Bytes. Times: 00:00:03

使用道具 举报

回复
论坛徽章:
18
生肖徽章2007版:虎
日期:2008-04-11 18:37:24奥运会纪念徽章:击剑
日期:2008-07-03 11:38:17迷宫蛋
日期:2011-05-10 13:03:40茶鸡蛋
日期:2011-05-10 13:05:16蜘蛛蛋
日期:2011-05-10 13:07:01灰彻蛋
日期:2012-12-10 11:47:16鲜花蛋
日期:2013-07-07 10:07:20
332#
发表于 2008-5-26 09:44 | 只看该作者
那个INSTR方法有些漏洞(当年份不为四位数时有问题), 不过在这里合理利用了你的规则(年份规定为四位数)

使用道具 举报

回复
论坛徽章:
5
奥运会纪念徽章:摔跤
日期:2008-07-02 08:48:392009日食纪念
日期:2009-07-22 09:30:00优秀写手
日期:2013-12-18 09:29:11SQL数据库编程大师
日期:2016-01-13 10:30:43SQL大赛参与纪念
日期:2016-01-13 10:32:19
333#
发表于 2008-5-26 09:44 | 只看该作者
我的算法思路和hotiice差不多
不过字节比他的多多了

CREATE OR REPLACE function SYSTEM.my_add_months(p_date_string varchar2, p_months number) return varchar2 IS
t int:=p_date_string;
l int:=100;
y int:= t/l/l; m int:= mod(t/l,l); d int:= mod(t,l);
BEGIN
   t := case when m=2 and d>=28 then case when not ((mod(y,4)=0 and mod(y,25)>0 or mod(y,16)=0) and d=28) then 1 end
             when m in(4,6,9,11) and d=30 then 1 when d=31 then 1 end;
   m := m+p_months;
   y := trunc(y+(m-1)/12);
   m := mod(mod(m,12)+11,12)+1;
   l:=28;
   if mod(y,4)=0 and (mod(y,25)>0 or mod(y,16)=0) then l:=29; end if;
   d := case when m in(4,6,9,11) and (d>30 or t=1) then 30
        when m=2 and (d>l or t=1) then l
        when t=1 then 31
        else d end;
   RETURN y||lpad(m,2,'0')||d;
END;
/


SQL> /
Congratulation ... Code Length: 538 Bytes. Times: 00:00:04


这是按我的算法思路走,最少的字节数了吧
当然我的最终成绩,还是按照555字节来定
这三个数,也好听

使用道具 举报

回复
论坛徽章:
5
奥运会纪念徽章:摔跤
日期:2008-07-02 08:48:392009日食纪念
日期:2009-07-22 09:30:00优秀写手
日期:2013-12-18 09:29:11SQL数据库编程大师
日期:2016-01-13 10:30:43SQL大赛参与纪念
日期:2016-01-13 10:32:19
334#
发表于 2008-5-26 09:45 | 只看该作者
原帖由 DragonBill 于 2008-5-26 09:44 发表
那个INSTR方法有些漏洞(当年份不为四位数时有问题), 不过在这里合理利用了你的规则(年份规定为四位数)


y>1582
至少是4位数
oracle的年不能超过9999

所以,没问题

使用道具 举报

回复
论坛徽章:
18
生肖徽章2007版:虎
日期:2008-04-11 18:37:24奥运会纪念徽章:击剑
日期:2008-07-03 11:38:17迷宫蛋
日期:2011-05-10 13:03:40茶鸡蛋
日期:2011-05-10 13:05:16蜘蛛蛋
日期:2011-05-10 13:07:01灰彻蛋
日期:2012-12-10 11:47:16鲜花蛋
日期:2013-07-07 10:07:20
335#
发表于 2008-5-26 09:48 | 只看该作者
但若避免这个漏洞仅仅只有一个Byte的差别, 如下:

--Congratulation ... Code Length: 345 Bytes. Times: 00:00:08
create or replace function my_add_months(p_date_string varchar2,
                                         p_months      number)
  return varchar2
AS
   C INT := p_date_string;
   H INT := 100;
   Y INT := C/H/H;
   M INT := MOD(C/H, H);
   D INT := MOD(C, H);
   Z INT := Y * 12 + M + p_months;

   PROCEDURE P
   AS
   BEGIN
      C := 27 + SUBSTR(43434434342 - SIGN(MOD(Y, 16 - 12 * SIGN(MOD(Y, H)))), 1 - M, 1);
   END;

BEGIN

   P;

   M := MOD(Z - 1, 12) + 1;
   Y := (Z - M) / 12;
   Z := C;

   P;

   RETURN Y*H*H + M*H + LEAST(D + TRUNC(D/Z) * 3, C);
END;
/

使用道具 举报

回复
论坛徽章:
18
生肖徽章2007版:虎
日期:2008-04-11 18:37:24奥运会纪念徽章:击剑
日期:2008-07-03 11:38:17迷宫蛋
日期:2011-05-10 13:03:40茶鸡蛋
日期:2011-05-10 13:05:16蜘蛛蛋
日期:2011-05-10 13:07:01灰彻蛋
日期:2012-12-10 11:47:16鲜花蛋
日期:2013-07-07 10:07:20
336#
发表于 2008-5-26 09:50 | 只看该作者
原帖由 于 2008-5-26 09:45 发表


y>1582
至少是4位数
oracle的年不能超过9999

所以,没问题



问题是没问题, 但这种写法, 如果放在实际应用中, 我会用SIGN+MOD的办法(345Byte), 而不是INSTR的办法(344Byte),
竞赛嘛..., 合理利用规则

使用道具 举报

回复
论坛徽章:
5
奥运会纪念徽章:摔跤
日期:2008-07-02 08:48:392009日食纪念
日期:2009-07-22 09:30:00优秀写手
日期:2013-12-18 09:29:11SQL数据库编程大师
日期:2016-01-13 10:30:43SQL大赛参与纪念
日期:2016-01-13 10:32:19
337#
发表于 2008-5-26 09:50 | 只看该作者
楼上的BT大侠,点解一下思路

使用道具 举报

回复
论坛徽章:
69
生肖徽章2007版:羊
日期:2008-11-14 14:42:19复活蛋
日期:2011-08-06 08:59:05ITPUB十周年纪念徽章
日期:2011-11-01 16:19:412012新春纪念徽章
日期:2012-01-04 11:49:542012新春纪念徽章
日期:2012-02-13 15:13:202012新春纪念徽章
日期:2012-02-13 15:13:202012新春纪念徽章
日期:2012-02-13 15:13:202012新春纪念徽章
日期:2012-02-13 15:13:202012新春纪念徽章
日期:2012-02-13 15:13:20版主4段
日期:2012-05-15 15:24:11
338#
 楼主| 发表于 2008-5-26 09:52 | 只看该作者
原帖由 DragonBill 于 2008-5-26 09:29 发表
借签你算月的方法可以再减少3个Byte

呵呵, 把你的算月方法代替我的, 能够缩短到 333 字节呢
你的算月的天数方法太巧妙了.

使用道具 举报

回复
论坛徽章:
5
奥运会纪念徽章:摔跤
日期:2008-07-02 08:48:392009日食纪念
日期:2009-07-22 09:30:00优秀写手
日期:2013-12-18 09:29:11SQL数据库编程大师
日期:2016-01-13 10:30:43SQL大赛参与纪念
日期:2016-01-13 10:32:19
339#
发表于 2008-5-26 09:53 | 只看该作者
就目前知道的源代码来看,还是yangtingkun的效率高——3秒,其他人都是4秒

使用道具 举报

回复
论坛徽章:
18
生肖徽章2007版:虎
日期:2008-04-11 18:37:24奥运会纪念徽章:击剑
日期:2008-07-03 11:38:17迷宫蛋
日期:2011-05-10 13:03:40茶鸡蛋
日期:2011-05-10 13:05:16蜘蛛蛋
日期:2011-05-10 13:07:01灰彻蛋
日期:2012-12-10 11:47:16鲜花蛋
日期:2013-07-07 10:07:20
340#
发表于 2008-5-26 09:54 | 只看该作者
原帖由 nyfor 于 2008-5-26 09:52 发表

呵呵, 把你的算月方法代替我的, 能够缩短到 333 字节呢
你的算月的天数方法太巧妙了.



嘿嘿嘿...我也在看你的算法, 力求找最短的代码

使用道具 举报

回复

您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

TOP技术积分榜 社区积分榜 徽章 团队 统计 知识索引树 积分竞拍 文本模式 帮助
  ITPUB首页 | ITPUB论坛 | 数据库技术 | 企业信息化 | 开发技术 | 微软技术 | 软件工程与项目管理 | IBM技术园地 | 行业纵向讨论 | IT招聘 | IT文档
  ChinaUnix | ChinaUnix博客 | ChinaUnix论坛
CopyRight 1999-2011 itpub.net All Right Reserved. 北京盛拓优讯信息技术有限公司版权所有 联系我们 未成年人举报专区 
京ICP备16024965号-8  北京市公安局海淀分局网监中心备案编号:11010802021510 广播电视节目制作经营许可证:编号(京)字第1149号
  
快速回复 返回顶部 返回列表