I'd like to add a solution based on finite difference method (FDM). The advantage of this solution is we don't need to manually transform the equation to any standard form. I'll use pdetoae
for the generation of difference equation.
xmax = 1; ymax = 1;
epsilon = 0.5; n = 0.1;
With[{u = u[x, y]},
eq = epsilon^2 D[u, x, x] + D[u, y, y] == 1;
{bc@x, bc@y} = {{D[u, x] == 0 /. x -> 0, u == -2 epsilon n D[u, x] /. x -> xmax},
{D[u, y] == 0 /. y -> 0, u == -2 n D[u, y] /. y -> ymax}};]
domain@x = {0, xmax};
domain@y = {0, ymax};
points@x = 25;
points@y = 25;
difforder = 4;
(grid@# = Array[# &, points@#, domain@#]) & /@ {x, y};
var = Outer[u, grid@x, grid@y] // Flatten;
(* Definition of pdetoae isn't included in this post,
please find it in the link above. *)
ptoafunc = pdetoae[u[x, y], grid /@ {x, y}, difforder];
removeredundance = #[[2 ;; -2]] &;
ae = removeredundance /@ removeredundance@ptoafunc@eq;
aebc@x = removeredundance /@ ptoafunc@bc@x;
aebc@y = ptoafunc@bc@y;
solrule = Solve[{ae, aebc@x, aebc@y} // Flatten, var][[1]];
solpoints = N@solrule /. (u[x_, y_] -> value_) :> {x, y, value};
sol = Interpolation[solpoints]
(* The following is an alternative method for obtaining sol,
it's more challenging to understand, but more efficient. *)
(*
{b, m} = CoefficientArrays[{ae, aebc@x, aebc@y} // Flatten, var];
sollst = LinearSolve[m, -b];
sol = ListInterpolation[ArrayReshape[sollst, {points@x, points@y}], domain /@ {x, y}]
*)
Plot3D[sol[x, y], {x, 0, xmax}, {y, 0, ymax}]

Update
If you still feel confused about removeredundance
, the followings are 2 alternatives that don't require you to remove equations from the system:
fullsys = Flatten@ptoafunc@{eq, bc@x, bc@y};
(* Alternative 1: *)
lSSolve[obj_List, constr___, x_, opt : OptionsPattern[FindMinimum]] :=
FindMinimum[{1/2 obj^2 // Total, constr}, x, opt]
lSSolve[obj_, rest__] := lSSolve[{obj}, rest]
solrule = Last@
lSSolve[Subtract @@@ fullsys, var]; // AbsoluteTiming
solpoints = N@solrule /. (u[x_, y_] -> value_) :> {x, y, value};
sol = Interpolation[solpoints]
(* Alternative 2: *)
{b, m} = CoefficientArrays[fullsys, var];
sollst = LeastSquares[m, -b]; // AbsoluteTiming
sol = ListInterpolation[ArrayReshape[sollst, {points@x, points@y}], domain /@ {x, y}]
You can check this post to learn more about lSSolve
.
Update 2
With my allowfemdbc
we can use FiniteElement
method without manually setting up NeumannValue
:
solfem = allowfemdbc@NDSolveValue[{eq, bc /@ {x, y}},
u, {x, 0, xmax}, {y, 0, ymax}];
Plot3D[solfem[x, y], {x, 0, xmax}, {y, 0, ymax}]
The solution looks the same as above, so I'd like to omit it here.