多部分标识符...无法绑定 [37000] - SQL 2005 查询

发布于 2024-12-14 16:51:14 字数 1906 浏览 2 评论 0原文

我意识到这是一个很常见的问题,但在查看了本网站和其他地方列出的类似问题后,到目前为止我还无法纠正它。

不管怎样,我在论坛上有一个基于 PHP 的应用程序,它允许用户互相给予信誉点,我相信你们都知道这些简单的设置是如何工作的,所以我不会详细讨论它。问题是,我相信这段代码最初是为 MySQL 编写的,虽然 95% 的代码已经转换为 MS SQL,并且现在可以在 MS SQL 中运行,但我怀疑仍然有一些查询在 SQL 2005 上似乎失败了由于连接等方面存在轻微的语法不一致。这让我陷入困境。 示例查询如下:

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id, 
 u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id, 
 r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username 
FROM forum_reputations r, forum_users u 
LEFT JOIN forum_posts p ON (r.rep_post_id = p.post_id) 
WHERE r.rep_to = 61
ORDER BY r.rep_id DESC

数据如下:

**Forum_Posts**:
post_id (int, PK)
post_subject (varchar)
forum_id (int)

**Forum_users**:
username (varchar)
user_id (int, PK)
user_colour (varchar)

**Forum_reputations**:
rep_id (int, PK)
rep_from (int) 
rep_to (int)
rep_time (int)
rep_post_id (int)
rep_point (int)
rep_comment (text)
enable_urls (int) 
rep_ip_address (varchar) 
username (varchar)

当查询运行时,SQL Server 会输出以下熟悉的错误:

[Microsoft][ODBC SQL Server Driver][SQL Server]The multi-part identifier "r.rep_post_id" could not be bound. [37000]

我很难理解为什么会发生这种情况。它显然暗示了rep_post_id有问题,但我检查了查询语法和列/表名称,它们都是正确的,我什至尝试将任何听起来远程像SQL保留字的对象括在方括号中(即u.[用户名]、r.[用户名] 等),但这没有什么区别。有趣的是,如果我更改 FROM 子句,使 Forum_users u 位于 Forum_users r 之前,则错误不再发生,并且返回数据,但这并没有多大用处,因为它会破坏 Left Join 并从 users 表中提取前 25 个,忽略它们在信誉表中是否有任何关联的条目。

输出应该包含一个表格,列出了用户 (r.rep_to) 的每个代表条目的以下内容:

给出的代表点数 (r.rep_point)

给出点数的用户 (r.rep_from, u.user_id, u.username)

给出日期点 (r.rep_time)

用户输入的评论,给出代表点(r.rep_comment)

(r.rep_post_id, p.post_id, p.post_subject) 提供代表的论坛帖子

如果有人对问题所在有任何想法或者如何重组它,我非常高兴听到它。我意识到这可能是非常初级的东西,但我真的看不见这里的树木!

谢谢

I realise this is quite a common one, but I've been unable to rectify it so far after going through the similar issues listed on this site and elsewhere.

Anyway, I have a PHP based app in a forum which allows users to give reputation points to each other, I'm sure you're all aware how those simple setups work so I won't dwell on it. The issue is, this bit of code was originally written for MySQL I believe, and while 95% of it has been converted to, and now works, in MS SQL, there remain some queries which seem to crap out on SQL 2005, I suspect due to slight syntax inconsistencies in joins etc. This one has me stuck.
The sample query is as follows:

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id, 
 u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id, 
 r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username 
FROM forum_reputations r, forum_users u 
LEFT JOIN forum_posts p ON (r.rep_post_id = p.post_id) 
WHERE r.rep_to = 61
ORDER BY r.rep_id DESC

The data is as follows:

**Forum_Posts**:
post_id (int, PK)
post_subject (varchar)
forum_id (int)

**Forum_users**:
username (varchar)
user_id (int, PK)
user_colour (varchar)

**Forum_reputations**:
rep_id (int, PK)
rep_from (int) 
rep_to (int)
rep_time (int)
rep_post_id (int)
rep_point (int)
rep_comment (text)
enable_urls (int) 
rep_ip_address (varchar) 
username (varchar)

When the query runs, SQL Server spits out the following, familiar error:

[Microsoft][ODBC SQL Server Driver][SQL Server]The multi-part identifier "r.rep_post_id" could not be bound. [37000]

I'm struggling to understand why this is happening. Its obviously insinuating that rep_post_id has a problem but I've checked the query syntax and column / table names and they're all correct, I even tried enclosing any objects that sounded remotely like SQL reserved words in square brackets (i.e u.[username], r.[username] etc), but it makes no difference. Interestingly if I change the FROM clause so Forum_users u is before Forum_users r, the error no longer occurs, and data is returned, but this isn't much use because it ruins the Left Join and pulls in the top 25 from the users table, ignoring whether they have any associated entries in the reputations table.

The output is supposed to comprise of a table listing the following for each rep entry for a user (r.rep_to):

Number of rep points given (r.rep_point)

User who gave the points (r.rep_from, u.user_id, u.username)

Date points were given (r.rep_time)

Comment entered by user giving the rep points (r.rep_comment)

Forum post that rep was given for (r.rep_post_id, p.post_id, p.post_subject)

If anyone has any thoughts on where this is going wrong or how it can be restructured, I'd greatly appreciate hearing about it. I realise this is probably something very rudimentary but I really can't see the wood for the trees here!

Thanks

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

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

发布评论

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

评论(2

尝蛊 2024-12-21 16:51:23

您不能组合隐式连接和显式连接并期望它正常工作。您必须使所有连接显式化,无论如何您都应该这样做,因为隐式连接是 SQL 反模式。

这是您所拥有的显式连接版本:

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id,
u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id,  
r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username  
FROM forum_reputations r
CROSS JOIN forum_users u  
LEFT JOIN forum_posts p ON r.rep_post_id = p.post_id  
WHERE r.rep_to = 61 
ORDER BY r.rep_id DESC 

但是,我怀疑这不是您想要的。我认为@EdHarper 的想法是正确的。

You cannot combine implicit and explicit joins and expect it to work correctly. You must make all the joins explicit which you should be doing in any event as implicit joins are a SQL antipattern.

This is the explict join version of what you have:

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id,
u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id,  
r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username  
FROM forum_reputations r
CROSS JOIN forum_users u  
LEFT JOIN forum_posts p ON r.rep_post_id = p.post_id  
WHERE r.rep_to = 61 
ORDER BY r.rep_id DESC 

However, I suspect it is NOT what you want. I think @EdHarper has the right idea.

花想c 2024-12-21 16:51:21

尝试

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id, 
 u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id, 
 r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username 
FROM forum_reputations r
JOIN forum_users u 
ON u.user_id = r.rep_from
LEFT JOIN forum_posts p ON r.rep_post_id = p.post_id 
WHERE r.rep_to = 61
ORDER BY r.rep_id DESC

它与您的问题没有直接关系,但是您的查询中缺少 forum_usersforum_reputation 之间的连接条件 - 这将产生笛卡尔积。我在上面添加了一个连接,但我猜测它是否在右列上。

try

SELECT TOP 25 p.post_id, p.post_subject, p.forum_id, u.username, u.user_id, 
 u.user_colour, r.rep_id, r.rep_from, r.rep_to, r.rep_time, r.rep_post_id, 
 r.rep_point, r.rep_comment, r.enable_urls, r.rep_ip_address, r.username 
FROM forum_reputations r
JOIN forum_users u 
ON u.user_id = r.rep_from
LEFT JOIN forum_posts p ON r.rep_post_id = p.post_id 
WHERE r.rep_to = 61
ORDER BY r.rep_id DESC

It's not directly relevant to your question, but a join condition between forum_users and forum_reputation is missing from your query - this will be producing a Cartesian product. I have added a join above, but am guessing a bit as to whether it's on the right column.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文