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

Removing/replacing/changing the head of an enhanced dependency relation #40

Open
nschneid opened this issue Dec 24, 2023 · 5 comments
Open

Comments

@nschneid
Copy link
Contributor

I am looking for a way to replace an edep keeping the relation name but changing the head to a node matched in the query. I don't see any discussion of this case in the docs.

Some things that I tried:

  1. Matching against edep: This adds a new edep but doesn't remove the old one.
upos=/PROPN/;upos=/NOUN/&func=/flat/;func!=/flat/&edep=/(.*)/	#1>#2;#1~#3	#2~#3;#3:edep=$1
  1. Matching against node 3's edom string with #1 in the regex representing node 1 (no effect):
upos=/PROPN/;upos=/NOUN/&func=/flat/;func!=/flat/&edom=/#1:(.*)/	#1>#2	#3:edom=#2:$1
  1. Matching node 1's token number in a capturing group and referencing it from the regex for node 3's edom string (no effect):
upos=/PROPN/&num=/(.*)/;upos=/NOUN/&func=/flat/;func!=/flat/&edom=/^$1:(.*)/	#1>#2	#3:edom=#2:$2
  1. edom as the action only, in hopes of replacing all the node's edeps (no effect):
upos=/PROPN/;upos=/NOUN/&func=/flat/&num=/(.*)/;func!=/flat/&edep=/(.*)/	#1>#2;#1~#3	#3:edom=$1||$2
  1. Clearing the old edep and then replacing it with #3:edep=;#3:edep=$1 as the action (syntax error).
@nschneid
Copy link
Contributor Author

nschneid commented Dec 24, 2023

(Stopgap solution: the first one but additionally prefix the old edeprel with "OLD", so it can be manually deleted:

upos=/PROPN/;upos=/NOUN/&func=/flat/;func!=/flat/&edep=/(.*)/	#1>#2;#1~#3	#2~#3;#3:edep=$1;#1~#3;#3:edep=OLD$1

)

@amir-zeldes
Copy link
Owner

Yeah, this kind of 'leaving yourself a memo' logic is often a good way of doing complex things with depedit (it's what the 'storage' fields are built for). I don't see a trivial way of just changing an edep head while keeping the edeprel, because it's not something you can condition on just the edeprel: if a node has two enhanced amod dependents, how would we know which one you want to reroute? With regular deps it's trivial, since there is only one per node, but with edeps we have no good way to do so, since there is no 'backpointer' linking to, say, "the edge that connects #1 and #2". There could of course be query language ways to express that, but the underlying datamodel in depedit is pretty simple, so it wouldn't be able to express inter-dependencies like that without being made substantially more complex. As you've seen you can work around it, primarily because you can edit fields step-wise, and because the DEPS column is accessible as a string. If you have a clever idea how to do it without changing the datamodel much (or if want to implement and PR!) just let me know ;)

@nschneid
Copy link
Contributor Author

What about treating edeps like features over pairs of nodes, with actions like

  • #1~#3+=amod (add E:amod(#1,#3) if it doesn't already exist)
  • #1~#3-=amod (remove E:amod(#1,#3) if it exists)

Changing just the head #3 from #1 to #2 of an enhanced amod would then be: #1~#3-=amod;#2~#3+=amod

Changing just the deprel from amod to acl would be: #1~#3-=amod;#1~#3+=acl

(Or if you don't like that notation, maybe #3:deps[amod]+=#1.)

I don't understand the code well enough to know how to implement it but I would think that it wouldn't require data model changes—the nodes would already be matched so it is just a matter of insertion/deletion operations on the DEPS column string.

@amir-zeldes
Copy link
Owner

Changing just the head #3 from #1 to #2 of an enhanced amod would then be: #1~#3-=amod;#2~#3+=amod

I'm not sure that's unambiguous - that seems to remove an amod secedge from 1 to 3 (if it exists) and add one from 2 to 3, but we can't just grab 'some edge' in the first step, and make sure that 'that edge' is changed to the new head. It's just based on string matching, and I think you could already do that now with several steps.

#1~#3-=amod;#1~#3+=acl

This too can already be achieved IMO, by capturing the ID field and editing the edom string accordingly (at least I think so)

#3:deps[amod]+=#1

This might be more powerful notation, since it addresses the head and deprel simultaneously. I'd need to think about it some more.

I don't understand the code well enough to know how to implement

I'm happy to reopen the issue and leave it here in case someone (incl. me) has time to look into this in the future.

@amir-zeldes amir-zeldes reopened this Jan 15, 2024
@nschneid
Copy link
Contributor Author

I tried editing edom in attempts 2, 3, and 4 of the original post—do you know why those had no effect?

I'm not sure that's unambiguous - that seems to remove an amod secedge from 1 to 3 (if it exists) and add one from 2 to 3, but we can't just grab 'some edge' in the first step, and make sure that 'that edge' is changed to the new head.

I meant #1~#3-=amod as equivalent to #3:deps[amod]-=#1. One has the deprel on the RHS of the operator, the other has the head node, but either way both would be used in matching the edge. (Yet another notation would be #3:deps-=#1:amod.) I don't have a strong opinion regarding the notation but I like the idea of being able to directly target an edep for removal.

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