{"action":"opened","number":4373,"pull_request":{"url":"https://api.github.com/repos/scala/scala/pulls/4373","id":30428920,"html_url":"https://github.com/scala/scala/pull/4373","diff_url":"https://github.com/scala/scala/pull/4373.diff","patch_url":"https://github.com/scala/scala/pull/4373.patch","issue_url":"https://api.github.com/repos/scala/scala/issues/4373","number":4373,"state":"open","locked":false,"title":"SI-8359 Adjust parameter order of accessor method in Delambdafy","user":{"login":"retronym","id":65551,"avatar_url":"https://avatars.githubusercontent.com/u/65551?v=3","gravatar_id":"","url":"https://api.github.com/users/retronym","html_url":"https://github.com/retronym","followers_url":"https://api.github.com/users/retronym/followers","following_url":"https://api.github.com/users/retronym/following{/other_user}","gists_url":"https://api.github.com/users/retronym/gists{/gist_id}","starred_url":"https://api.github.com/users/retronym/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/retronym/subscriptions","organizations_url":"https://api.github.com/users/retronym/orgs","repos_url":"https://api.github.com/users/retronym/repos","events_url":"https://api.github.com/users/retronym/events{/privacy}","received_events_url":"https://api.github.com/users/retronym/received_events","type":"User","site_admin":false},"body":"Under `-Ydelambdafy:method`, a public, static accessor method is\ncreated to expose the private method containing the body of the\nlambda.\n\nCurrently this accessor method has its parameters in the same order\nstructure as those of the lambda body method.\n\nWhat is this order? There are three categories of parameters:\n\n  1. lambda parameters\n  2. captured parameters (added by lambdalift)\n  3. self parameters (added to lambda bodies that end up in trait\n     impl classes by mixin, and added unconditionally to the static\n     accessor method.)\n\nThese are currently emitted in order #3, #1, #2.\n\nHere are examples of the current behaviour:\n\nBEFORE (trait):\n\n```\n% cat sandbox/test.scala && scalac-hash v2.11.5 -Ydelambdafy:method sandbox/test.scala && javap -private -classpath . 'Test$class'\ntrait Member; class Capture; trait LambdaParam\ntrait Test {\n  def member: Member\n  def foo {\n    val local = new Capture\n    (arg: LambdaParam) => \"\" + arg + member + local\n  }\n}\nCompiled from \"test.scala\"\npublic abstract class Test$class {\n  public static void foo(Test);\n  private static final java.lang.String $anonfun$1(Test, LambdaParam, Capture);\n  public static void $init$(Test);\n  public static final java.lang.String accessor$1(Test, LambdaParam, Capture);\n}\n```\n\nBEFORE (class):\n\n```\n% cat sandbox/test.scala && scalac-hash v2.11.5 -Ydelambdafy:method sandbox/test.scala && javap -private -classpath . Test\ntrait Member; class Capture; trait LambdaParam\nabstract class Test {\n  def member: Member\n  def foo {\n    val local = new Capture\n    (arg: LambdaParam) => \"\" + arg + member + local\n  }\n}\nCompiled from \"test.scala\"\npublic abstract class Test {\n  public abstract Member member();\n  public void foo();\n  private final java.lang.String $anonfun$1(LambdaParam, Capture);\n  public Test();\n  public static final java.lang.String accessor$1(Test, LambdaParam, Capture);\n}\n```\n\nContrasting the class case with Java:\n\n```\n% cat sandbox/Test.java && javac -d . sandbox/Test.java && javap -private -classpath . Test\npublic abstract class Test {\n  public static class Member {};\n  public static class Capture {};\n  public static class LambaParam {};\n  public static interface I {\n    public abstract Object c(LambaParam arg);\n  }\n  public abstract Member member();\n  public void test() {\n    Capture local = new Capture();\n    I i1 = (LambaParam arg) -> \"\" + member() + local;\n  }\n}\n\nCompiled from \"Test.java\"\npublic abstract class Test {\n  public Test();\n  public abstract Test$Member member();\n  public void test();\n  private java.lang.Object lambda$test$0(Test$Capture, Test$LambaParam);\n}\n```\n\nWe can see that in Java 8 lambda parameters come after captures. If we\nwant to use Java's LambdaMetafactory to spin up our anoymous FunctionN\nsubclasses on the fly, our ordering must change.\n\nI can see three options for change:\n\n  1. Adjust `LambdaLift` to always prepend captured parameters,\n     rather than appending them. I think we could leave `Mixin` as\n     it is, it already prepends the self parameter. This would result\n     a parameter ordering, in terms of the list above: #3, #2, #1.\n  2. More conservatively, do this just for methods known to hold\n     lambda bodies. This might avoid needlessly breaking code that\n     has come to depend on our binary encoding.\n  3. Adjust the parameters of the accessor method only. The body\n     of this method can permute params before calling the lambda\n     body method.\n\nThis commit implements option #1.\n\nI've included a test that shows this in all in action. However, that\nis currently disabled, as we don't have a partest category for tests\nthat require Java 8.\n\nAlternative to #4369.\n\nThe enclosed manual test executes correctly:\n\n```\n% qscalac -Ydelambdafy:method test/pending/run/delambdafy-lambdametafactory.scala && qscala Test\ncba\nabc 1erutpac\nC@2dda6444 cba\ncba\n```","created_at":"2015-03-04T00:55:59Z","updated_at":"2015-03-04T00:55:59Z","closed_at":null,"merged_at":null,"merge_commit_sha":null,"assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/scala/scala/pulls/4373/commits","review_comments_url":"https://api.github.com/repos/scala/scala/pulls/4373/comments","review_comment_url":"https://api.github.com/repos/scala/scala/pulls/comments{/number}","comments_url":"https://api.github.com/repos/scala/scala/issues/4373/comments","statuses_url":"https://api.github.com/repos/scala/scala/statuses/fde4585a93778b5721fa723ed116a72c36e9b974","head":{"label":"retronym:topic/indylambda-permutations-2","ref":"topic/indylambda-permutations-2","sha":"fde4585a93778b5721fa723ed116a72c36e9b974","user":{"login":"retronym","id":65551,"avatar_url":"https://avatars.githubusercontent.com/u/65551?v=3","gravatar_id":"","url":"https://api.github.com/users/retronym","html_url":"https://github.com/retronym","followers_url":"https://api.github.com/users/retronym/followers","following_url":"https://api.github.com/users/retronym/following{/other_user}","gists_url":"https://api.github.com/users/retronym/gists{/gist_id}","starred_url":"https://api.github.com/users/retronym/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/retronym/subscriptions","organizations_url":"https://api.github.com/users/retronym/orgs","repos_url":"https://api.github.com/users/retronym/repos","events_url":"https://api.github.com/users/retronym/events{/privacy}","received_events_url":"https://api.github.com/users/retronym/received_events","type":"User","site_admin":false},"repo":{"id":2902104,"name":"scala","full_name":"retronym/scala","owner":{"login":"retronym","id":65551,"avatar_url":"https://avatars.githubusercontent.com/u/65551?v=3","gravatar_id":"","url":"https://api.github.com/users/retronym","html_url":"https://github.com/retronym","followers_url":"https://api.github.com/users/retronym/followers","following_url":"https://api.github.com/users/retronym/following{/other_user}","gists_url":"https://api.github.com/users/retronym/gists{/gist_id}","starred_url":"https://api.github.com/users/retronym/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/retronym/subscriptions","organizations_url":"https://api.github.com/users/retronym/orgs","repos_url":"https://api.github.com/users/retronym/repos","events_url":"https://api.github.com/users/retronym/events{/privacy}","received_events_url":"https://api.github.com/users/retronym/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/retronym/scala","description":"The Scala programming language","fork":true,"url":"https://api.github.com/repos/retronym/scala","forks_url":"https://api.github.com/repos/retronym/scala/forks","keys_url":"https://api.github.com/repos/retronym/scala/keys{/key_id}","collaborators_url":"https://api.github.com/repos/retronym/scala/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/retronym/scala/teams","hooks_url":"https://api.github.com/repos/retronym/scala/hooks","issue_events_url":"https://api.github.com/repos/retronym/scala/issues/events{/number}","events_url":"https://api.github.com/repos/retronym/scala/events","assignees_url":"https://api.github.com/repos/retronym/scala/assignees{/user}","branches_url":"https://api.github.com/repos/retronym/scala/branches{/branch}","tags_url":"https://api.github.com/repos/retronym/scala/tags","blobs_url":"https://api.github.com/repos/retronym/scala/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/retronym/scala/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/retronym/scala/git/refs{/sha}","trees_url":"https://api.github.com/repos/retronym/scala/git/trees{/sha}","statuses_url":"https://api.github.com/repos/retronym/scala/statuses/{sha}","languages_url":"https://api.github.com/repos/retronym/scala/languages","stargazers_url":"https://api.github.com/repos/retronym/scala/stargazers","contributors_url":"https://api.github.com/repos/retronym/scala/contributors","subscribers_url":"https://api.github.com/repos/retronym/scala/subscribers","subscription_url":"https://api.github.com/repos/retronym/scala/subscription","commits_url":"https://api.github.com/repos/retronym/scala/commits{/sha}","git_commits_url":"https://api.github.com/repos/retronym/scala/git/commits{/sha}","comments_url":"https://api.github.com/repos/retronym/scala/comments{/number}","issue_comment_url":"https://api.github.com/repos/retronym/scala/issues/comments{/number}","contents_url":"https://api.github.com/repos/retronym/scala/contents/{+path}","compare_url":"https://api.github.com/repos/retronym/scala/compare/{base}...{head}","merges_url":"https://api.github.com/repos/retronym/scala/merges","archive_url":"https://api.github.com/repos/retronym/scala/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/retronym/scala/downloads","issues_url":"https://api.github.com/repos/retronym/scala/issues{/number}","pulls_url":"https://api.github.com/repos/retronym/scala/pulls{/number}","milestones_url":"https://api.github.com/repos/retronym/scala/milestones{/number}","notifications_url":"https://api.github.com/repos/retronym/scala/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/retronym/scala/labels{/name}","releases_url":"https://api.github.com/repos/retronym/scala/releases{/id}","created_at":"2011-12-02T23:04:11Z","updated_at":"2015-01-15T03:25:44Z","pushed_at":"2015-03-04T00:55:07Z","git_url":"git://github.com/retronym/scala.git","ssh_url":"git@github.com:retronym/scala.git","clone_url":"https://github.com/retronym/scala.git","svn_url":"https://github.com/retronym/scala","homepage":"http://www.scala-lang.org/","size":97545,"stargazers_count":4,"watchers_count":4,"language":"Scala","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":4,"forks":0,"open_issues":4,"watchers":4,"default_branch":"master"}},"base":{"label":"scala:2.11.x","ref":"2.11.x","sha":"52d4a5ac00af05648d3afae79b7428ef19ae5c21","user":{"login":"scala","id":57059,"avatar_url":"https://avatars.githubusercontent.com/u/57059?v=3","gravatar_id":"","url":"https://api.github.com/users/scala","html_url":"https://github.com/scala","followers_url":"https://api.github.com/users/scala/followers","following_url":"https://api.github.com/users/scala/following{/other_user}","gists_url":"https://api.github.com/users/scala/gists{/gist_id}","starred_url":"https://api.github.com/users/scala/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/scala/subscriptions","organizations_url":"https://api.github.com/users/scala/orgs","repos_url":"https://api.github.com/users/scala/repos","events_url":"https://api.github.com/users/scala/events{/privacy}","received_events_url":"https://api.github.com/users/scala/received_events","type":"Organization","site_admin":false},"repo":{"id":2888818,"name":"scala","full_name":"scala/scala","owner":{"login":"scala","id":57059,"avatar_url":"https://avatars.githubusercontent.com/u/57059?v=3","gravatar_id":"","url":"https://api.github.com/users/scala","html_url":"https://github.com/scala","followers_url":"https://api.github.com/users/scala/followers","following_url":"https://api.github.com/users/scala/following{/other_user}","gists_url":"https://api.github.com/users/scala/gists{/gist_id}","starred_url":"https://api.github.com/users/scala/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/scala/subscriptions","organizations_url":"https://api.github.com/users/scala/orgs","repos_url":"https://api.github.com/users/scala/repos","events_url":"https://api.github.com/users/scala/events{/privacy}","received_events_url":"https://api.github.com/users/scala/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/scala/scala","description":"The Scala programming language","fork":false,"url":"https://api.github.com/repos/scala/scala","forks_url":"https://api.github.com/repos/scala/scala/forks","keys_url":"https://api.github.com/repos/scala/scala/keys{/key_id}","collaborators_url":"https://api.github.com/repos/scala/scala/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/scala/scala/teams","hooks_url":"https://api.github.com/repos/scala/scala/hooks","issue_events_url":"https://api.github.com/repos/scala/scala/issues/events{/number}","events_url":"https://api.github.com/repos/scala/scala/events","assignees_url":"https://api.github.com/repos/scala/scala/assignees{/user}","branches_url":"https://api.github.com/repos/scala/scala/branches{/branch}","tags_url":"https://api.github.com/repos/scala/scala/tags","blobs_url":"https://api.github.com/repos/scala/scala/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/scala/scala/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/scala/scala/git/refs{/sha}","trees_url":"https://api.github.com/repos/scala/scala/git/trees{/sha}","statuses_url":"https://api.github.com/repos/scala/scala/statuses/{sha}","languages_url":"https://api.github.com/repos/scala/scala/languages","stargazers_url":"https://api.github.com/repos/scala/scala/stargazers","contributors_url":"https://api.github.com/repos/scala/scala/contributors","subscribers_url":"https://api.github.com/repos/scala/scala/subscribers","subscription_url":"https://api.github.com/repos/scala/scala/subscription","commits_url":"https://api.github.com/repos/scala/scala/commits{/sha}","git_commits_url":"https://api.github.com/repos/scala/scala/git/commits{/sha}","comments_url":"https://api.github.com/repos/scala/scala/comments{/number}","issue_comment_url":"https://api.github.com/repos/scala/scala/issues/comments{/number}","contents_url":"https://api.github.com/repos/scala/scala/contents/{+path}","compare_url":"https://api.github.com/repos/scala/scala/compare/{base}...{head}","merges_url":"https://api.github.com/repos/scala/scala/merges","archive_url":"https://api.github.com/repos/scala/scala/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/scala/scala/downloads","issues_url":"https://api.github.com/repos/scala/scala/issues{/number}","pulls_url":"https://api.github.com/repos/scala/scala/pulls{/number}","milestones_url":"https://api.github.com/repos/scala/scala/milestones{/number}","notifications_url":"https://api.github.com/repos/scala/scala/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/scala/scala/labels{/name}","releases_url":"https://api.github.com/repos/scala/scala/releases{/id}","created_at":"2011-12-01T05:02:34Z","updated_at":"2015-03-03T23:23:18Z","pushed_at":"2015-03-02T19:47:33Z","git_url":"git://github.com/scala/scala.git","ssh_url":"git@github.com:scala/scala.git","clone_url":"https://github.com/scala/scala.git","svn_url":"https://github.com/scala/scala","homepage":"http://www.scala-lang.org/","size":186362,"stargazers_count":3735,"watchers_count":3735,"language":"Scala","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":977,"mirror_url":null,"open_issues_count":41,"forks":977,"open_issues":41,"watchers":3735,"default_branch":"2.11.x"}},"_links":{"self":{"href":"https://api.github.com/repos/scala/scala/pulls/4373"},"html":{"href":"https://github.com/scala/scala/pull/4373"},"issue":{"href":"https://api.github.com/repos/scala/scala/issues/4373"},"comments":{"href":"https://api.github.com/repos/scala/scala/issues/4373/comments"},"review_comments":{"href":"https://api.github.com/repos/scala/scala/pulls/4373/comments"},"review_comment":{"href":"https://api.github.com/repos/scala/scala/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/scala/scala/pulls/4373/commits"},"statuses":{"href":"https://api.github.com/repos/scala/scala/statuses/fde4585a93778b5721fa723ed116a72c36e9b974"}},"merged":false,"mergeable":null,"mergeable_state":"unknown","merged_by":null,"comments":0,"review_comments":0,"commits":1,"additions":53,"deletions":3,"changed_files":2}}