如何在 squeak 中动态更改方法的名称?

发布于 2024-07-19 15:39:47 字数 79 浏览 7 评论 0原文

我有一个类,我想在运行时更改特定方法的名称。 我猜“行为”类中有一个方法可以做到这一点。 但我就是找不到它。 有什么帮助吗? [吱吱声]

I have a class and I want to change the name of a specific method in run time.
I guess there's a method in the 'Behavior' class that does it. But I just can't find it. any help? [in squeak]

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

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

发布评论

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

评论(5

╰つ倒转 2024-07-26 15:39:47

用户执行此操作的正常方法是修改方法源并“接受它”,然后删除旧版本。 因此,基本的 Squeak 不太可能包含单一方法来执行此操作,尽管我可能是错的。

但是,如果您安装了 OmniBrowser,则有一个名为“rename”的重构方法,您可以检查并查找执行此重构的代码。 它相当复杂,首先因为重构是使用命令模式完成的,这涉及到一些重定向来解决,但其次因为这是一个相当复杂的重构,其中包括修改调用站点。

The normal way a user does this is to modify the method source and 'accept it' then delete the old version. So it's not likely that basic Squeak includes a single method to do this, although I could be wrong.

However if you install, for example, OmniBrowser there is a method refactoring called 'rename' and you could inspect and find code to perform this refactoring. It is fairly complex, firstly because the refactorings are done using the command pattern which involves a little redirection to work out, but secondly because this is a fairly complex refactoring which includes modifying the call sites.

窝囊感情。 2024-07-26 15:39:47

你的建议对我来说是一个巨大的危险信号。
你想用这个来实现什么目的?

您的意思是您想更改在运行时调用的方法的名称吗?
如果是这样,那很容易。

做类似的事情:

|methodName|
methodName :=  self useMethod1 ifTrue: [#method1 ] ifFalse:[ #method2 ].
self perform: methodName.

What you are suggesting puts HUGE red flags up for me.
What is it you are trying to accomplish with this?

Do you mean you want to change the name of the method you are calling at runtime?
If so, that's easy.

do something like:

|methodName|
methodName :=  self useMethod1 ifTrue: [#method1 ] ifFalse:[ #method2 ].
self perform: methodName.
我ぃ本無心為│何有愛 2024-07-26 15:39:47

你最好使用重构

r := RenameMethodRefactoring 
    renameMethod: #foo:foo: 
    in: Foo
    to: #bar:bar:
    permutation: (1 to: #foo:foo: numArgs). 
r execute.

You best use a refactoring

r := RenameMethodRefactoring 
    renameMethod: #foo:foo: 
    in: Foo
    to: #bar:bar:
    permutation: (1 to: #foo:foo: numArgs). 
r execute.
荒岛晴空 2024-07-26 15:39:47

尽可能避免在实际代码中使用巫毒魔法。

话虽这么说,您可以通过动态操作方法来做一些非常有趣的事情。

例如,Etoys 中的代码块被转换为 Smalltalk 方法。 其他 DSL 实现也可以从类似的元编程技巧中受益。

经过一番尝试后,我想出了以下用于重命名一元方法的代码:

renameMethod: oldMethod inClass: class to: newMethod
| oldSelector newSelector source parser |

oldSelector := oldMethod asSymbol.
newSelector := newMethod asSymbol.
oldSelector = newSelector ifTrue: [^self].

"Get method category"
category := (LocatedMethod location: class selector: oldSelector) category.

"Get method source code"
source := class sourceCodeAt: oldSelector.

"Replace selector in method source" 
(parser := class parserClass new) parseSelector: source.
source := (newSelector asString), (source allButFirst: parser endOfLastToken).

"Compile modified source"
class compile: source classified: category.

"Remove old selector"
class removeSelector: oldSelector

如果您浏览 Squeak 代码的时间比我长一点,您可能会找到一种更简单的方法来执行此操作。

Avoid voodoo magic in real code when possible.

That being said you can do some very interesting things by manipulating methods dynamically.

For instance the code bricks in Etoys are translated into Smalltalk methods. Other DSL implementations can also benefit from similar metaprogramming tricks.

After experimenting a bit I came up with the following code for renaming unary methods:

renameMethod: oldMethod inClass: class to: newMethod
| oldSelector newSelector source parser |

oldSelector := oldMethod asSymbol.
newSelector := newMethod asSymbol.
oldSelector = newSelector ifTrue: [^self].

"Get method category"
category := (LocatedMethod location: class selector: oldSelector) category.

"Get method source code"
source := class sourceCodeAt: oldSelector.

"Replace selector in method source" 
(parser := class parserClass new) parseSelector: source.
source := (newSelector asString), (source allButFirst: parser endOfLastToken).

"Compile modified source"
class compile: source classified: category.

"Remove old selector"
class removeSelector: oldSelector

You could probably find an easier way to do this if you browse through the Squeak code a bit longer than I did.

任性一次 2024-07-26 15:39:47

实际上,您无法更改方法的名称,因为它没有名称。

对象的方法字典将 Symbols 映射到 CompiledMethods。 “更改方法的名称”意味着“将 CompiledMethod 值从这个键移动到那个键”。

You can't change a method's name, really, because it doesn't have one.

An object's method dictionary maps Symbols to CompiledMethods. "Change the name of a method" means "move the CompiledMethod value from this key to that key".

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