如何在 SQL 2000 中尝试解析?

发布于 2024-07-29 23:55:36 字数 702 浏览 5 评论 0原文

我在旧的 SQL 2000 数据库中有一个存储过程,它采用 varchar 格式的注释列并将其导出为货币对象。 在设置此表结构时,假设这将是进入该字段的唯一数据。 当前过程的功能很简单:

SELECT CAST(dbo.member_category_assign.coment AS money)
  FROM dbo.member_category_assign
 WHERE member_id = @intMemberId
       AND 
       dbo.member_category_assign.eff_date <= @dtmEndDate
       AND 
       (
        dbo.member_category_assign.term_date >= @dtmBeginDate
        OR 
        dbo.member_category_assign.term_date Is Null
       )

但是,现在正在将数据插入到该列中,该列无法解析为货币对象,并导致过程崩溃。 我无法删除“坏”数据(因为这是第三方产品),但需要更新存储过程来测试货币可解析条目并将其返回。

如何更新此过程,以便它只返回可解析为货币对象的值? 我是否创建一个临时表并迭代每个项目,或者是否有更聪明的方法来做到这一点? 我一直使用旧版 SQL 2000(版本 6.0),因此不幸的是无法使用任何较新的函数。

I have a stored procedure in an old SQL 2000 database that takes a comment column that is formatted as a varchar and exports it out as a money object. At the time this table structure was setup, it was assumed this would be the only data going into this field. The current procedure functions simply this this:

SELECT CAST(dbo.member_category_assign.coment AS money)
  FROM dbo.member_category_assign
 WHERE member_id = @intMemberId
       AND 
       dbo.member_category_assign.eff_date <= @dtmEndDate
       AND 
       (
        dbo.member_category_assign.term_date >= @dtmBeginDate
        OR 
        dbo.member_category_assign.term_date Is Null
       )

However, data is now being inserted into this column that is not parsable to a money object and is causing the procedure to crash. I am unable to remove the "bad" data (since this is a third party product), but need to update the stored procedure to test for a money parsable entry and return that.

How can I update this procedure so that it will only return the value that is parsable as a money object? Do I create a temporary table and iterate through every item, or is there a more clever way to do this? I'm stuck with legacy SQL 2000 (version 6.0) so using any of the newer functions unfortunately is not available.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

玩心态 2024-08-05 23:55:36

很抱歉做出新的答案,评论就足够了,但我缺乏这样做所需的权限。 关于您问题的答案,我只想补充一点,您应该谨慎使用上述 ISNUMERIC。 虽然它的工作原理与预期的一样,但它还将“1.3E-2”之类的内容解析为数值,奇怪的是,您无法将其转换为数值或金钱而不产生异常。 我通常最终使用:

SELECT 
    CASE WHEN ISNUMERIC( some_value ) = 1 AND CHARINDEX( 'E', Upper( some_value ) ) = 0 
         THEN Cast( some_value as money ) 
         ELSE Cast( 0 as money )
    END as money_value

Apologies for making a new answer, where a comment would suffice, but I lack the required permissions to do so. Onto the answer to your question, I would only like to add that you should use the above ISNUMERIC carefully. While it works much as expected, it also parses things like '1.3E-2' as a value numeric, which strangely enough you cannot cast into a numeric or money without generating an exception. I generally end up using:

SELECT 
    CASE WHEN ISNUMERIC( some_value ) = 1 AND CHARINDEX( 'E', Upper( some_value ) ) = 0 
         THEN Cast( some_value as money ) 
         ELSE Cast( 0 as money )
    END as money_value
猫卆 2024-08-05 23:55:36

检查 IsNumeric 可能会对您有所帮助 - 您只需返回零值即可。 如果您想返回“N/a”或其他一些字符串值,

我使用查询中的列创建了下面的示例。

第一个查询仅返回所有行。

第二个查询返回 MONEY 值。

第三个返回一个字符串值,用 N/A 代替非整数值。

set nocount on
drop table #MoneyTest
create table #MoneyTest
(
    MoneyTestId Int Identity (1, 1),
    coment varchar (100),
    member_id int,
    eff_date datetime,
    term_date datetime
)
insert into #MoneyTest (coment, member_id, eff_date, term_date)
values 
    (104, 1, '1/1/2008', '1/1/2009'),
    (200, 1, '1/1/2008', '1/1/2009'),
    (322, 1, '1/1/2008', '1/1/2009'),
    (120, 1, '1/1/2008', '1/1/2009')

insert into #MoneyTest (coment, member_id, eff_date, term_date) 
values  ('XX', 1, '1/1/2008', '1/1/2009')

Select *
FROM #MoneyTest

declare @intMemberId int = 1
declare @dtmBeginDate   DateTime = '1/1/2008'
declare @dtmEndDate DateTime = '1/1/2009'

SELECT 
    CASE WHEN ISNUMERIC (Coment)=1 THEN CAST(#MoneyTest.coment AS money) ELSE cast (0 as money) END MoneyValue
FROM #MoneyTest
WHERE member_id = @intMemberId
AND #MoneyTest.eff_date <= @dtmEndDate
AND 
(
    #MoneyTest.term_date >= @dtmBeginDate
    OR 
    #MoneyTest.term_date Is Null
)

SELECT 
    CASE WHEN ISNUMERIC (Coment)=1 THEN CAST (CAST(#MoneyTest.coment AS money) AS VARCHAR) ELSE 'N/a' END StringValue
FROM #MoneyTest
WHERE member_id = @intMemberId
AND #MoneyTest.eff_date <= @dtmEndDate
AND 
(
    #MoneyTest.term_date >= @dtmBeginDate
    OR 
    #MoneyTest.term_date Is Null
)

Checking for IsNumeric may help you - you can simply return a Zero value. If you want to return a 'N/a' or some other string value

I created the sample below with the columns from your query.

The first query just returns all rows.

The second query returns a MONEY value.

The third one returns a String value with N/A in place of the non-integer value.

set nocount on
drop table #MoneyTest
create table #MoneyTest
(
    MoneyTestId Int Identity (1, 1),
    coment varchar (100),
    member_id int,
    eff_date datetime,
    term_date datetime
)
insert into #MoneyTest (coment, member_id, eff_date, term_date)
values 
    (104, 1, '1/1/2008', '1/1/2009'),
    (200, 1, '1/1/2008', '1/1/2009'),
    (322, 1, '1/1/2008', '1/1/2009'),
    (120, 1, '1/1/2008', '1/1/2009')

insert into #MoneyTest (coment, member_id, eff_date, term_date) 
values  ('XX', 1, '1/1/2008', '1/1/2009')

Select *
FROM #MoneyTest

declare @intMemberId int = 1
declare @dtmBeginDate   DateTime = '1/1/2008'
declare @dtmEndDate DateTime = '1/1/2009'

SELECT 
    CASE WHEN ISNUMERIC (Coment)=1 THEN CAST(#MoneyTest.coment AS money) ELSE cast (0 as money) END MoneyValue
FROM #MoneyTest
WHERE member_id = @intMemberId
AND #MoneyTest.eff_date <= @dtmEndDate
AND 
(
    #MoneyTest.term_date >= @dtmBeginDate
    OR 
    #MoneyTest.term_date Is Null
)

SELECT 
    CASE WHEN ISNUMERIC (Coment)=1 THEN CAST (CAST(#MoneyTest.coment AS money) AS VARCHAR) ELSE 'N/a' END StringValue
FROM #MoneyTest
WHERE member_id = @intMemberId
AND #MoneyTest.eff_date <= @dtmEndDate
AND 
(
    #MoneyTest.term_date >= @dtmBeginDate
    OR 
    #MoneyTest.term_date Is Null
)
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文