Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Not Equals (~=) empty table comparison confuses typing? #2952

Open
PennyJim opened this issue Nov 13, 2024 · 3 comments
Open

Not Equals (~=) empty table comparison confuses typing? #2952

PennyJim opened this issue Nov 13, 2024 · 3 comments

Comments

@PennyJim
Copy link
Contributor

How are you using the lua-language-server?

Visual Studio Code Extension (sumneko.lua)

Which OS are you using?

Linux

What is the issue affecting?

Type Checking

Expected Behaviour

It to understand the comparison is bogus and not affect the expected type of the parent table.

Actual Behaviour

It somehow makes the parent table unknown?

Reproduction steps

Very specifically the ~= does this. Change it to A.b == {} or even not A.b == {} and it works fine.
But with ~=, A becomes unknown within the condition (not even after it)

---@class A
---@field b {[C]:D}
local A

if A.b ~= {} then
	local C = A
end

Additional Notes

Comparing to a table literal should probably warn that it'll never be true (or false)

Log File

service.log

@tomlau10
Copy link
Contributor

I checked out an older stable version v3.9.3 and it works.
After doing a git bisect, here is the result:

5c3086acd08765f9122ed5b7f806e2b2bf3737e3 is the first bad commit
commit 5c3086acd08765f9122ed5b7f806e2b2bf3737e3
Author: Lewis Russell <[email protected]>
Date:   Sun Sep 22 17:19:12 2024 +0100

    feat: type narrow types with literal fields

 changelog.md                   |  1 +
 script/vm/tracer.lua           | 59 ++++++++++++++++++++++++++++++++++++++++++
 test/type_inference/common.lua | 50 +++++++++++++++++++++++++++++++++++
 3 files changed, 110 insertions(+)

So this issue is probably introduced in #2864 by @lewis6991 🤔

@tomlau10
Copy link
Contributor

Comparing to a table literal should probably warn that it'll never be true (or false)

Btw there can be cases that comparing to a table literal returns true 😄 by using __eq in metatable:

local mt = {
    __eq = function (t, a, b)
        return true
    end
}
local t = setmetatable({}, mt)

print(t == {}) --> true

For example someone may want to implement a Vector class, and allow it to compare with literal table { x, y, z }.
If all values of x, y, z are equal, then it will be considered to be equal.

@PennyJim
Copy link
Contributor Author

Oh I thought I remember reading that compare functions don't get triggered if they don't share a metatable. Might be specific compare functions...

It's been a while since I dived deep into metatables. Combined with how melty they made my brain at times? I would not be surprised if I forget fundamental things about them.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants