{"action":"created","comment":{"url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/comments/125472867","pull_request_review_id":47864694,"id":125472867,"diff_hunk":"@@ -221,212 +220,91 @@ def _build_forcing_solver(self):\n \n     def apply(self, scaling, x_in, x_nl, x_out, **kwargs):\n \n-        self.x0.assign(x_nl)\n-        self.scaling.assign(scaling)\n-        if 'mu_alpha' in kwargs and kwargs['mu_alpha'] is not None:\n-            self.mu_scaling.assign(kwargs['mu_alpha'])\n-        self.u_forcing_solver.solve()  # places forcing in self.uF\n-\n-        u_out, p_out, _ = x_out.split()\n-\n-        x_out.assign(x_in)\n-        u_out += self.uF\n-\n+        super(IncompressibleForcing, self).apply(scaling, x_in, x_nl, x_out, **kwargs)\n         if 'incompressible' in kwargs and kwargs['incompressible']:\n+            _, p_out, _ = self.x_out.split()\n             self.divergence_solver.solve()\n             p_out.assign(self.divu)\n \n \n-class EadyForcing(Forcing):\n+class EadyForcing(IncompressibleForcing):\n     \"\"\"\n     Forcing class for Eady Boussinesq equations.\n     \"\"\"\n \n-    def _build_forcing_solver(self):\n-        \"\"\"\n-        Put forcing terms into the u & b equations.\n-        \"\"\"\n+    def forcing_term(self):\n \n-        state = self.state\n-        self.scaling = Constant(1.)\n-        Vu = state.spaces(\"HDiv\")\n-        Vp = state.spaces(\"DG\")\n-        W = state.W\n-\n-        dbdy = state.parameters.dbdy\n-        H = state.parameters.H\n+        L = Forcing.forcing_term(self)\n+        dbdy = self.state.parameters.dbdy\n+        H = self.state.parameters.H\n+        Vp = self.state.spaces(\"DG\")\n         eady_exp = Function(Vp).interpolate(Expression((\"x[2]-H/2\"),H=H))\n \n-        self.x0 = Function(W)   # copy x to here\n-\n-        u0,p0,b0 = split(self.x0)\n-\n-        # u_forcing\n-\n-        F = TrialFunction(Vu)\n-        w = TestFunction(Vu)\n-        self.uF = Function(Vu)\n-\n-        Omega = state.Omega\n-        mu = state.mu\n-\n-        a = inner(w,F)*dx\n-        L = self.scaling*(\n-            div(w)*p0  # pressure gradient\n-            + b0*inner(w,state.k)  # gravity term\n-            - dbdy*eady_exp*inner(w,as_vector([0.,1.,0.]))  # Eady forcing\n-        )*dx\n-\n-        if self.euler_poincare:\n-            L -= self.scaling*0.5*div(w)*inner(u0, u0)*dx\n-\n-        if Omega is not None:\n-            L -= self.scaling*inner(w,cross(2*Omega,u0))*dx  # Coriolis term\n-\n-        if mu is not None:\n-            self.mu_scaling = Constant(1.)\n-            L -= self.mu_scaling*mu*inner(w,state.k)*inner(u0,state.k)*dx\n-\n-        bcs = [DirichletBC(Vu, 0.0, \"bottom\"),\n-               DirichletBC(Vu, 0.0, \"top\")]\n+        L -= self.scaling*dbdy*eady_exp*inner(self.test,as_vector([0.,1.,0.]))*dx\n+        return L\n \n-        u_forcing_problem = LinearVariationalProblem(\n-            a,L,self.uF, bcs=bcs\n-        )\n+    def _build_forcing_solvers(self):\n \n-        self.u_forcing_solver = LinearVariationalSolver(u_forcing_problem)\n+        super(EadyForcing, self)._build_forcing_solvers()\n \n         # b_forcing\n-\n-        Vb = state.spaces(\"HDiv_v\")\n-\n+        dbdy = self.state.parameters.dbdy\n+        Vb = self.state.spaces(\"HDiv_v\")\n         F = TrialFunction(Vb)\n         gamma = TestFunction(Vb)\n         self.bF = Function(Vb)\n+        u0, _, b0 = split(self.x0)\n \n         a = gamma*F*dx\n-        L = -gamma*self.scaling*(dbdy*inner(u0,as_vector([0.,1.,0.])))*dx\n+        L = -self.scaling*gamma*(dbdy*inner(u0, as_vector([0.,1.,0.])))*dx\n \n         b_forcing_problem = LinearVariationalProblem(\n-            a,L,self.bF\n+            a, L, self.bF\n         )\n \n         self.b_forcing_solver = LinearVariationalSolver(b_forcing_problem)\n \n-        # divergence_free\n-\n-        Vp = state.spaces(\"DG\")\n-        p = TrialFunction(Vp)\n-        q = TestFunction(Vp)\n-        self.divu = Function(Vp)\n-\n-        a = p*q*dx\n-        L = q*div(u0)*dx\n-\n-        divergence_problem = LinearVariationalProblem(\n-            a, L, self.divu)\n-\n-        self.divergence_solver = LinearVariationalSolver(divergence_problem)\n-\n     def apply(self, scaling, x_in, x_nl, x_out, **kwargs):\n \n-        self.x0.assign(x_nl)\n-        self.scaling.assign(scaling)\n-        if 'mu_alpha' in kwargs and kwargs['mu_alpha'] is not None:\n-            self.mu_scaling.assign(kwargs['mu_alpha'])\n-        self.u_forcing_solver.solve()  # places forcing in self.uF\n+        super(EadyForcing, self).apply(scaling, x_in, x_nl, x_out, **kwargs)\n         self.b_forcing_solver.solve()  # places forcing in self.bF\n-\n-        u_out, p_out, b_out = x_out.split()\n-\n-        x_out.assign(x_in)\n-        u_out += self.uF\n+        _, _, b_out = self.x_out.split()","path":"gusto/forcing.py","position":429,"original_position":429,"commit_id":"2ab3890d621e9d9942bf0483a3b6e9d590685b74","original_commit_id":"2ab3890d621e9d9942bf0483a3b6e9d590685b74","user":{"login":"wence-","id":1126981,"avatar_url":"https://avatars1.githubusercontent.com/u/1126981?v=3","gravatar_id":"","url":"https://api.github.com/users/wence-","html_url":"https://github.com/wence-","followers_url":"https://api.github.com/users/wence-/followers","following_url":"https://api.github.com/users/wence-/following{/other_user}","gists_url":"https://api.github.com/users/wence-/gists{/gist_id}","starred_url":"https://api.github.com/users/wence-/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/wence-/subscriptions","organizations_url":"https://api.github.com/users/wence-/orgs","repos_url":"https://api.github.com/users/wence-/repos","events_url":"https://api.github.com/users/wence-/events{/privacy}","received_events_url":"https://api.github.com/users/wence-/received_events","type":"User","site_admin":false},"body":"Again here the action at a distance.","created_at":"2017-07-04T13:27:27Z","updated_at":"2017-07-04T13:27:27Z","html_url":"https://github.com/firedrakeproject/gusto/pull/110#discussion_r125472867","pull_request_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110","_links":{"self":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/comments/125472867"},"html":{"href":"https://github.com/firedrakeproject/gusto/pull/110#discussion_r125472867"},"pull_request":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110"}}},"pull_request":{"url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110","id":126300499,"html_url":"https://github.com/firedrakeproject/gusto/pull/110","diff_url":"https://github.com/firedrakeproject/gusto/pull/110.diff","patch_url":"https://github.com/firedrakeproject/gusto/pull/110.patch","issue_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/110","number":110,"state":"open","locked":false,"title":"Forcing restructure","user":{"login":"jshipton","id":6875594,"avatar_url":"https://avatars1.githubusercontent.com/u/6875594?v=3","gravatar_id":"","url":"https://api.github.com/users/jshipton","html_url":"https://github.com/jshipton","followers_url":"https://api.github.com/users/jshipton/followers","following_url":"https://api.github.com/users/jshipton/following{/other_user}","gists_url":"https://api.github.com/users/jshipton/gists{/gist_id}","starred_url":"https://api.github.com/users/jshipton/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/jshipton/subscriptions","organizations_url":"https://api.github.com/users/jshipton/orgs","repos_url":"https://api.github.com/users/jshipton/repos","events_url":"https://api.github.com/users/jshipton/events{/privacy}","received_events_url":"https://api.github.com/users/jshipton/received_events","type":"User","site_admin":false},"body":"This PR addresses the problem of repeated code in forcing.py. Many terms in the forcing are the same whichever equations you're solving (e.g. Coriolis). The forcing term, L, is now created in the forcing_term method which checks which terms are required and adds them on by calling the correct method. Terms that are the same across equations are defined in the base Forcing class. The pressure_gradient term is common to all equations that we currently solve and is therefore an abstract method which must be defined in each subclass.\r\n\r\nThe Eady forcing classes are slightly different because they require a term to be added to the rhs of either the b or the theta equation (all other forcing terms only occur on t he rhs of the u equation). This means that the extra Eady terms cannot be specified as user defined extra_terms because these are automatically assumed to go on the rhs of the u equation. This is something that could be changed in the future.","created_at":"2017-06-19T13:17:30Z","updated_at":"2017-07-04T13:27:27Z","closed_at":null,"merged_at":null,"merge_commit_sha":"5440ca0c13fcd7e52fa33cb34b8ed0e2c4860c22","assignee":null,"assignees":[],"requested_reviewers":[],"milestone":null,"commits_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110/commits","review_comments_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110/comments","review_comment_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls/comments{/number}","comments_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/110/comments","statuses_url":"https://api.github.com/repos/firedrakeproject/gusto/statuses/2ab3890d621e9d9942bf0483a3b6e9d590685b74","head":{"label":"firedrakeproject:forcing_restructure","ref":"forcing_restructure","sha":"2ab3890d621e9d9942bf0483a3b6e9d590685b74","user":{"login":"firedrakeproject","id":5558005,"avatar_url":"https://avatars0.githubusercontent.com/u/5558005?v=3","gravatar_id":"","url":"https://api.github.com/users/firedrakeproject","html_url":"https://github.com/firedrakeproject","followers_url":"https://api.github.com/users/firedrakeproject/followers","following_url":"https://api.github.com/users/firedrakeproject/following{/other_user}","gists_url":"https://api.github.com/users/firedrakeproject/gists{/gist_id}","starred_url":"https://api.github.com/users/firedrakeproject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/firedrakeproject/subscriptions","organizations_url":"https://api.github.com/users/firedrakeproject/orgs","repos_url":"https://api.github.com/users/firedrakeproject/repos","events_url":"https://api.github.com/users/firedrakeproject/events{/privacy}","received_events_url":"https://api.github.com/users/firedrakeproject/received_events","type":"Organization","site_admin":false},"repo":{"id":49564954,"name":"gusto","full_name":"firedrakeproject/gusto","owner":{"login":"firedrakeproject","id":5558005,"avatar_url":"https://avatars0.githubusercontent.com/u/5558005?v=3","gravatar_id":"","url":"https://api.github.com/users/firedrakeproject","html_url":"https://github.com/firedrakeproject","followers_url":"https://api.github.com/users/firedrakeproject/followers","following_url":"https://api.github.com/users/firedrakeproject/following{/other_user}","gists_url":"https://api.github.com/users/firedrakeproject/gists{/gist_id}","starred_url":"https://api.github.com/users/firedrakeproject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/firedrakeproject/subscriptions","organizations_url":"https://api.github.com/users/firedrakeproject/orgs","repos_url":"https://api.github.com/users/firedrakeproject/repos","events_url":"https://api.github.com/users/firedrakeproject/events{/privacy}","received_events_url":"https://api.github.com/users/firedrakeproject/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/firedrakeproject/gusto","description":"Three dimensional atmospheric dynamical core using the Gung Ho numerics.","fork":false,"url":"https://api.github.com/repos/firedrakeproject/gusto","forks_url":"https://api.github.com/repos/firedrakeproject/gusto/forks","keys_url":"https://api.github.com/repos/firedrakeproject/gusto/keys{/key_id}","collaborators_url":"https://api.github.com/repos/firedrakeproject/gusto/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/firedrakeproject/gusto/teams","hooks_url":"https://api.github.com/repos/firedrakeproject/gusto/hooks","issue_events_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/events{/number}","events_url":"https://api.github.com/repos/firedrakeproject/gusto/events","assignees_url":"https://api.github.com/repos/firedrakeproject/gusto/assignees{/user}","branches_url":"https://api.github.com/repos/firedrakeproject/gusto/branches{/branch}","tags_url":"https://api.github.com/repos/firedrakeproject/gusto/tags","blobs_url":"https://api.github.com/repos/firedrakeproject/gusto/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/firedrakeproject/gusto/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/firedrakeproject/gusto/git/refs{/sha}","trees_url":"https://api.github.com/repos/firedrakeproject/gusto/git/trees{/sha}","statuses_url":"https://api.github.com/repos/firedrakeproject/gusto/statuses/{sha}","languages_url":"https://api.github.com/repos/firedrakeproject/gusto/languages","stargazers_url":"https://api.github.com/repos/firedrakeproject/gusto/stargazers","contributors_url":"https://api.github.com/repos/firedrakeproject/gusto/contributors","subscribers_url":"https://api.github.com/repos/firedrakeproject/gusto/subscribers","subscription_url":"https://api.github.com/repos/firedrakeproject/gusto/subscription","commits_url":"https://api.github.com/repos/firedrakeproject/gusto/commits{/sha}","git_commits_url":"https://api.github.com/repos/firedrakeproject/gusto/git/commits{/sha}","comments_url":"https://api.github.com/repos/firedrakeproject/gusto/comments{/number}","issue_comment_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/comments{/number}","contents_url":"https://api.github.com/repos/firedrakeproject/gusto/contents/{+path}","compare_url":"https://api.github.com/repos/firedrakeproject/gusto/compare/{base}...{head}","merges_url":"https://api.github.com/repos/firedrakeproject/gusto/merges","archive_url":"https://api.github.com/repos/firedrakeproject/gusto/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/firedrakeproject/gusto/downloads","issues_url":"https://api.github.com/repos/firedrakeproject/gusto/issues{/number}","pulls_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls{/number}","milestones_url":"https://api.github.com/repos/firedrakeproject/gusto/milestones{/number}","notifications_url":"https://api.github.com/repos/firedrakeproject/gusto/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/firedrakeproject/gusto/labels{/name}","releases_url":"https://api.github.com/repos/firedrakeproject/gusto/releases{/id}","deployments_url":"https://api.github.com/repos/firedrakeproject/gusto/deployments","created_at":"2016-01-13T09:51:17Z","updated_at":"2017-05-29T13:35:56Z","pushed_at":"2017-07-04T10:21:27Z","git_url":"git://github.com/firedrakeproject/gusto.git","ssh_url":"git@github.com:firedrakeproject/gusto.git","clone_url":"https://github.com/firedrakeproject/gusto.git","svn_url":"https://github.com/firedrakeproject/gusto","homepage":"http://firedrakeproject.org/gusto/","size":4346,"stargazers_count":1,"watchers_count":1,"language":"Python","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":30,"forks":0,"open_issues":30,"watchers":1,"default_branch":"master"}},"base":{"label":"firedrakeproject:master","ref":"master","sha":"3b646e5b22ab8f6938492f20cf3ad3a2bda7ed4a","user":{"login":"firedrakeproject","id":5558005,"avatar_url":"https://avatars0.githubusercontent.com/u/5558005?v=3","gravatar_id":"","url":"https://api.github.com/users/firedrakeproject","html_url":"https://github.com/firedrakeproject","followers_url":"https://api.github.com/users/firedrakeproject/followers","following_url":"https://api.github.com/users/firedrakeproject/following{/other_user}","gists_url":"https://api.github.com/users/firedrakeproject/gists{/gist_id}","starred_url":"https://api.github.com/users/firedrakeproject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/firedrakeproject/subscriptions","organizations_url":"https://api.github.com/users/firedrakeproject/orgs","repos_url":"https://api.github.com/users/firedrakeproject/repos","events_url":"https://api.github.com/users/firedrakeproject/events{/privacy}","received_events_url":"https://api.github.com/users/firedrakeproject/received_events","type":"Organization","site_admin":false},"repo":{"id":49564954,"name":"gusto","full_name":"firedrakeproject/gusto","owner":{"login":"firedrakeproject","id":5558005,"avatar_url":"https://avatars0.githubusercontent.com/u/5558005?v=3","gravatar_id":"","url":"https://api.github.com/users/firedrakeproject","html_url":"https://github.com/firedrakeproject","followers_url":"https://api.github.com/users/firedrakeproject/followers","following_url":"https://api.github.com/users/firedrakeproject/following{/other_user}","gists_url":"https://api.github.com/users/firedrakeproject/gists{/gist_id}","starred_url":"https://api.github.com/users/firedrakeproject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/firedrakeproject/subscriptions","organizations_url":"https://api.github.com/users/firedrakeproject/orgs","repos_url":"https://api.github.com/users/firedrakeproject/repos","events_url":"https://api.github.com/users/firedrakeproject/events{/privacy}","received_events_url":"https://api.github.com/users/firedrakeproject/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/firedrakeproject/gusto","description":"Three dimensional atmospheric dynamical core using the Gung Ho numerics.","fork":false,"url":"https://api.github.com/repos/firedrakeproject/gusto","forks_url":"https://api.github.com/repos/firedrakeproject/gusto/forks","keys_url":"https://api.github.com/repos/firedrakeproject/gusto/keys{/key_id}","collaborators_url":"https://api.github.com/repos/firedrakeproject/gusto/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/firedrakeproject/gusto/teams","hooks_url":"https://api.github.com/repos/firedrakeproject/gusto/hooks","issue_events_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/events{/number}","events_url":"https://api.github.com/repos/firedrakeproject/gusto/events","assignees_url":"https://api.github.com/repos/firedrakeproject/gusto/assignees{/user}","branches_url":"https://api.github.com/repos/firedrakeproject/gusto/branches{/branch}","tags_url":"https://api.github.com/repos/firedrakeproject/gusto/tags","blobs_url":"https://api.github.com/repos/firedrakeproject/gusto/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/firedrakeproject/gusto/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/firedrakeproject/gusto/git/refs{/sha}","trees_url":"https://api.github.com/repos/firedrakeproject/gusto/git/trees{/sha}","statuses_url":"https://api.github.com/repos/firedrakeproject/gusto/statuses/{sha}","languages_url":"https://api.github.com/repos/firedrakeproject/gusto/languages","stargazers_url":"https://api.github.com/repos/firedrakeproject/gusto/stargazers","contributors_url":"https://api.github.com/repos/firedrakeproject/gusto/contributors","subscribers_url":"https://api.github.com/repos/firedrakeproject/gusto/subscribers","subscription_url":"https://api.github.com/repos/firedrakeproject/gusto/subscription","commits_url":"https://api.github.com/repos/firedrakeproject/gusto/commits{/sha}","git_commits_url":"https://api.github.com/repos/firedrakeproject/gusto/git/commits{/sha}","comments_url":"https://api.github.com/repos/firedrakeproject/gusto/comments{/number}","issue_comment_url":"https://api.github.com/repos/firedrakeproject/gusto/issues/comments{/number}","contents_url":"https://api.github.com/repos/firedrakeproject/gusto/contents/{+path}","compare_url":"https://api.github.com/repos/firedrakeproject/gusto/compare/{base}...{head}","merges_url":"https://api.github.com/repos/firedrakeproject/gusto/merges","archive_url":"https://api.github.com/repos/firedrakeproject/gusto/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/firedrakeproject/gusto/downloads","issues_url":"https://api.github.com/repos/firedrakeproject/gusto/issues{/number}","pulls_url":"https://api.github.com/repos/firedrakeproject/gusto/pulls{/number}","milestones_url":"https://api.github.com/repos/firedrakeproject/gusto/milestones{/number}","notifications_url":"https://api.github.com/repos/firedrakeproject/gusto/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/firedrakeproject/gusto/labels{/name}","releases_url":"https://api.github.com/repos/firedrakeproject/gusto/releases{/id}","deployments_url":"https://api.github.com/repos/firedrakeproject/gusto/deployments","created_at":"2016-01-13T09:51:17Z","updated_at":"2017-05-29T13:35:56Z","pushed_at":"2017-07-04T10:21:27Z","git_url":"git://github.com/firedrakeproject/gusto.git","ssh_url":"git@github.com:firedrakeproject/gusto.git","clone_url":"https://github.com/firedrakeproject/gusto.git","svn_url":"https://github.com/firedrakeproject/gusto","homepage":"http://firedrakeproject.org/gusto/","size":4346,"stargazers_count":1,"watchers_count":1,"language":"Python","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":30,"forks":0,"open_issues":30,"watchers":1,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110"},"html":{"href":"https://github.com/firedrakeproject/gusto/pull/110"},"issue":{"href":"https://api.github.com/repos/firedrakeproject/gusto/issues/110"},"comments":{"href":"https://api.github.com/repos/firedrakeproject/gusto/issues/110/comments"},"review_comments":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110/comments"},"review_comment":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/firedrakeproject/gusto/pulls/110/commits"},"statuses":{"href":"https://api.github.com/repos/firedrakeproject/gusto/statuses/2ab3890d621e9d9942bf0483a3b6e9d590685b74"}}}}
{"actor":{"display_login":"wence-"}}