Erstellen Sie ein abgestuftes Netz

Oct 11 2020

Ich möchte ein abgestuftes Netz in einem Würfel erstellen, mit einem feineren Netz in der linken Hälfte und einem gröberen Netz in der rechten Hälfte. Mein Plan war es, den Würfel mit einer 2D-Ebene zu partitionieren und dann ein Grenznetz mit zu generieren ToBoundaryMesh(es sollte auch ein Grenznetz auf der Partition erstellt werden) und dann ToElementMeshmit verschiedenen MaxCellMeasurelinks und rechts von der Partition anzuwenden . Hier ist mein Code:

reg = RegionUnion[Cuboid[], 
  ImplicitRegion[x == 0.5 && 0 <= y <= 1 && 0 <= z <= 1, {x, y, z}]];
ToBoundaryMesh[reg]

was den folgenden Fehler ergibt:

BoundaryDiscretizeRegion::brepl: There are components in RegionUnion[Cuboid[{0,0,0}],ImplicitRegion[x==0.5&&0<=y<=1&&0<=z<=1,{x,y,z}]] having dimension lower than the embedding dimension 3 that will not be included in the boundary representation.

Wie kann ich ein abgestuftes Netz erzielen? Jede Hilfe wird sehr geschätzt.

Bearbeiten

Ich habe folgendes versucht. Ich habe zwei Quader mit einer gemeinsamen Grenze erstellt und sie mit verbunden Or. Dann habe ich ein Netz erstellt, während ich die beiden quaderförmigen Regionen (Beschriftungen 10 und 20) mit markiert habe RegionMarker, in denen ich auch MaxCellMeasuredie beiden Regionen als 1 und 0,01 angegeben habe. Hier ist der Code:

reg = ImplicitRegion[Or[0 <= x <= 0.5 && 0 <= y <= 1 && 0 <= z <= 1,
0.5 <= x <= 1 && 0 <= y <= 1 && 0 <= z <= 1], {x, y, z}];
mesh = ToElementMesh[reg, 
   "RegionMarker" -> {{{0.1, 0.5, 0.5}, 10, 1}, {{0.6, 0.5, 0.5}, 20, 0.01}}];

In beiden Regionen entsteht jedoch immer noch ein Netz von einheitlicher Größe. Irgendwelche Ideen, wie man das Problem überwinden kann?

Antworten

3 TimLaska Oct 13 2020 at 14:14

Hier ist eine Methode zum Aufbau eines anisotropen Hexaedernetzes, die jedoch nicht dem Wunsch des OP nach einer "einfachen" Lösung entspricht.

Die Inspiration stammt aus dem Tensor Product Grid Example . Die Idee ist, eine Reihe von 1D-Netzsegmenten entlang jeder Richtung zu erstellen und das Netz mit zu erstellen RegionProduct.

Hier ist ein Beispiel eines abgestuften Netzes, das mit einem gleichmäßigen Netz entlang der x-Richtung verbunden ist. Ein praktisches Beispiel für diese Art der Vernetzung wäre die konjugierte Wärmeübertragung, bei der das Fluid eine Grenzschicht oder ein abgestuftes Netz aufweist, um Wärmegradienten an der Wand zu erfassen, und der Feststoff gleichmäßig vernetzt werden kann.

Einige Hilfsfunktionen zum Erstellen abgestufter Netze:

(* Import required package *)
Needs["NDSolve`FEM`"];
(* Define Some Helper Functions For Structured Quad Mesh*)
pointsToMesh[data_] :=
  MeshRegion[Transpose[{data}], 
   Line@Table[{i, i + 1}, {i, Length[data] - 1}]];
unitMeshGrowth[n_, r_] := 
 Table[(r^(j/(-1 + n)) - 1.)/(r - 1.), {j, 0, n - 1}]
meshGrowth[x0_, xf_, n_, r_] := (xf - x0) unitMeshGrowth[n, r] + x0
firstElmHeight[x0_, xf_, n_, r_] := 
 Abs@First@Differences@meshGrowth[x0, xf, n, r]
lastElmHeight[x0_, xf_, n_, r_] := 
 Abs@Last@Differences@meshGrowth[x0, xf, n, r]
findGrowthRate[x0_, xf_, n_, fElm_] := 
 Quiet@Abs@
   FindRoot[firstElmHeight[x0, xf, n, r] - fElm, {r, 1.0001, 100000}, 
     Method -> "Brent"][[1, 2]]
meshGrowthByElm[x0_, xf_, n_, fElm_] := 
 N@Sort@Chop@meshGrowth[x0, xf, n, findGrowthRate[x0, xf, n, fElm]]
meshGrowthByElm0[len_, n_, fElm_] := meshGrowthByElm[0, len, n, fElm]
flipSegment[l_] := (#1 - #2) & @@ {First[#], #} &@Reverse[l];
extendMesh[mesh_, newmesh_] := Union[mesh, Max@mesh + newmesh]

Ein kommentierter Workflow zum Erstellen eines abgestuften Netzes:

(*Define parameters*)
(*Lengths*)
(*2 horizontal segments*)
h1 = 0.5;
h2 = 0.5;
v = 1;(*Vertical*)
d = 1;(*Depth*)
(*Number of elements per segment*)
nh1 = 15;
nh2 = 10;
nv = 20;
nd = 5;
(*Association for Clearer Region Assignment*)
reg = <|"left" -> 1, "right" -> 2|>;
(*Create mesh segments*)
(*Horizontal segments*)
(* left segment *)
(*First element is 1/50th of seg length*)
(*Flip segment so smallest elm at interface *)
sh1 = flipSegment@meshGrowthByElm0[h1, nh1, h1/50];
(*Make right segment uniform mesh size*)
sh2 = Subdivide[h2, nh2];
(*Glue segments together*)
segh = extendMesh[sh1, sh2];
(*View individual horizontal segments*)
Print["Horizontal segments"]
pointsToMesh /@ {sh1, sh2}
(*View combined segments*)
Print["Combined horizontal segments"]
rh = pointsToMesh@segh
(*Vertical Segment*)
Print["Vertical segment"]
rv = pointsToMesh@Subdivide[v, nv]
(*View Region Product of horiz and vert segs*)
Print["2D Region via RegionProduct"]
RegionProduct[rh, rv]
(*Depth Segment*)
Print["Depth segment"]
rd = pointsToMesh@Subdivide[d, nd]
(*Create a tensor product grid from h,v,and d segments*)
rp = RegionProduct[rh, rv, rd];
(*View mesh*)
Print["Full Extruded 3D Region via RegionProduct"]
HighlightMesh[rp, Style[1, Orange]]
(*Extract Coords from RegionProduct*)
crd = MeshCoordinates[rp];
(*grab hexa element incidents RegionProduct mesh*)
inc = Delete[0] /@ MeshCells[rp, 3];
mesh = ToElementMesh["Coordinates" -> crd, 
   "MeshElements" -> {HexahedronElement[inc]}];
(*Extract bmesh*)
bmesh = ToBoundaryMesh[mesh];
(*Iron RegionMember Function*)
Ω3Diron = Cuboid[{0, 0, 0}, {h1, v, d}];
rmf = RegionMember[Ω3Diron];
regmarkerfn = If[rmf[#], reg["left"], reg["right"]] &;
(*Get mean coordinate of each hexa for region marker assignment*)
mean = Mean /@ GetElementCoordinates[mesh["Coordinates"], #] & /@ 
    ElementIncidents[mesh["MeshElements"]] // First;
regmarkers = regmarkerfn /@ mean;
(*Create and view element mesh*)
Print["Converted Hexa Element Mesh"]
mesh = ToElementMesh["Coordinates" -> mesh["Coordinates"], 
   "MeshElements" -> {HexahedronElement[inc, regmarkers]}];
Graphics3D[
 ElementMeshToGraphicsComplex[bmesh, 
  VertexColors -> (ColorData["BrightBands"] /@ 
     Rescale[regmarkerfn /@ bmesh["Coordinates"]])], Boxed -> False]