diff --git a/applications/test/dimField/Make/files b/applications/test/dimField/Make/files
deleted file mode 100644
index 8289e2ec00d6a022bae5c79fa46f7ebd4951d48e..0000000000000000000000000000000000000000
--- a/applications/test/dimField/Make/files
+++ /dev/null
@@ -1,3 +0,0 @@
-Test-dimField.C
-
-EXE = $(FOAM_USER_APPBIN)/Test-dimField
diff --git a/applications/test/dimField1/Make/files b/applications/test/dimField1/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..226fc66a5d62d1f362874e8608a5f059b8f39a27
--- /dev/null
+++ b/applications/test/dimField1/Make/files
@@ -0,0 +1,3 @@
+Test-dimField1.cxx
+
+EXE = $(FOAM_USER_APPBIN)/Test-dimField1
diff --git a/applications/test/dimField/Make/options b/applications/test/dimField1/Make/options
similarity index 100%
rename from applications/test/dimField/Make/options
rename to applications/test/dimField1/Make/options
diff --git a/applications/test/dimField/Test-dimField.C b/applications/test/dimField1/Test-dimField1.cxx
similarity index 80%
rename from applications/test/dimField/Test-dimField.C
rename to applications/test/dimField1/Test-dimField1.cxx
index f711584883beb8f65912ece747f8242718e7a2d5..9eaf98fe95ac25584a4ad589ee4dcbebb6200ea3 100644
--- a/applications/test/dimField/Test-dimField.C
+++ b/applications/test/dimField1/Test-dimField1.cxx
@@ -5,7 +5,7 @@
     \\  /    A nd           | www.openfoam.com
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
-    Copyright (C) 2020-2022 OpenCFD Ltd.
+    Copyright (C) 2020-2024 OpenCFD Ltd.
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -24,7 +24,7 @@ License
     along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
 
 Application
-    Test-dimField
+    Test-dimField1
 
 Description
     Simple tests for DimensionedField
@@ -52,7 +52,12 @@ namespace Foam
 
 int main(int argc, char *argv[])
 {
+    argList::addBoolOption("write", "write some test fields");
+
     #include "setRootCase.H"
+
+    const bool doWrite = args.found("write");
+
     #include "createTime.H"
     #include "createMesh.H"
 
@@ -60,19 +65,23 @@ int main(int argc, char *argv[])
         Info<< "Tensor field\n" << endl;
         DimensionedField<tensor, volMesh> tensorfld
         (
-            IOobject
+            mesh.newIOobject
             (
                 "tensor",
-                runTime.timeName(),
-                mesh,
-                { IOobject::READ_IF_PRESENT, IOobject::NO_REGISTER }
+                { IOobject::READ_IF_PRESENT, IOobject::NO_WRITE }
             ),
             mesh,
             dimensioned<tensor>(dimless, tensor(1,2,3,4,5,6,7,8,9))
         );
 
-        Info().beginBlock("transformed")
-            << tensorfld.T() << nl;
+        if (doWrite)
+        {
+            tensorfld.write();
+        }
+
+
+        Info<< nl;
+        Info().beginBlock("transformed") << tensorfld.T();
         Info().endBlock();
 
         {
@@ -84,8 +93,8 @@ int main(int argc, char *argv[])
                     dimensioned<scalar>(14)
                 );
 
-            Info().beginBlock(tfld().type())
-                << tfld << nl;
+            Info<< nl;
+            Info().beginBlock(tfld().type()) << tfld;
             Info().endBlock();
         }
 
@@ -98,8 +107,8 @@ int main(int argc, char *argv[])
                     dimensioned<scalar>(5)
                 );
 
-            Info().beginBlock(tfld().type())
-                << tfld() << nl;
+            Info<< nl;
+            Info().beginBlock(tfld().type()) << tfld();
             Info().endBlock();
 
             // From dissimilar types
@@ -111,8 +120,8 @@ int main(int argc, char *argv[])
                     dimensioned<vector>(Zero)
                 );
 
-            Info().beginBlock(tfld2().type())
-                << tfld2() << nl;
+            Info<< nl;
+            Info().beginBlock(tfld2().type()) << tfld2();
             Info().endBlock();
         }
     }
@@ -122,20 +131,13 @@ int main(int argc, char *argv[])
         Info<< "uint8 field\n" << endl;
         DimensionedField<uint8_t, volMesh> statefld
         (
-            IOobject
-            (
-                "state",
-                runTime.timeName(),
-                mesh,
-                IOobject::NO_READ,
-                IOobject::NO_WRITE
-            ),
+            mesh.newIOobject("state")
             mesh,
             dimensioned<uint8_t>(dimless, uint8_t{100})
         );
 
-        Info().beginBlock("stateField")
-            << statefld << nl;
+        Info<< nl;
+        Info().beginBlock("stateField") << statefld;
         Info().endBlock();
     }
     #endif
diff --git a/applications/test/parallelOverset/Make/options b/applications/test/parallelOverset/Make/options
index b0aa2ef220daef87bf34aed01ad5ceef9cc4e607..db6c073e474b7e76ac88d5d351daee0c65e45e6f 100644
--- a/applications/test/parallelOverset/Make/options
+++ b/applications/test/parallelOverset/Make/options
@@ -7,5 +7,6 @@ EXE_INC = \
 
 EXE_LIBS = \
     -lfiniteVolume \
+    -ldynamicFvMesh \
     -lsampling \
     -loverset
diff --git a/applications/test/parallelOverset/laplacianDyMFoam.C b/applications/test/parallelOverset/laplacianDyMFoam.C
index 997ef3f590e5a2abceedf40823e5d3d01d153e08..f94bbd2cafeb52e1883648a31a93dfdbc11451c4 100644
--- a/applications/test/parallelOverset/laplacianDyMFoam.C
+++ b/applications/test/parallelOverset/laplacianDyMFoam.C
@@ -56,6 +56,7 @@ Description
 
 #include "fvCFD.H"
 #include "simpleControl.H"
+#include "predicates.H"
 #include "dynamicFvMesh.H"
 #include "dynamicOversetFvMesh.H"
 
@@ -97,6 +98,7 @@ int main(int argc, char *argv[])
         component(T.ref(), mesh.C(), 1);
         // Interpolate + halo swap
         T.correctBoundaryConditions();
+        // T.boundaryFieldRef().evaluate_if(predicates::always{});
         // Check halo swap
         dynamicOversetFvMesh::checkCoupledBC(T);
     }
diff --git a/applications/utilities/preProcessing/mapFieldsPar/MapVolFields.H b/applications/utilities/preProcessing/mapFieldsPar/MapVolFields.H
index f3106def5c470ff6dfee134cdcb6e4c1a09f9dff..34b26b49edbcfffd7c87cc54ef42dcc53f9154fa 100644
--- a/applications/utilities/preProcessing/mapFieldsPar/MapVolFields.H
+++ b/applications/utilities/preProcessing/mapFieldsPar/MapVolFields.H
@@ -26,8 +26,8 @@ License
 
 \*---------------------------------------------------------------------------*/
 
-#ifndef MapConsistentVolFields_H
-#define MapConsistentVolFields_H
+#ifndef Foam_MapConsistentVolFields_H
+#define Foam_MapConsistentVolFields_H
 
 #include "GeometricField.H"
 #include "meshToMesh.H"
@@ -41,10 +41,9 @@ namespace Foam
 template<class Type>
 void evaluateConstraintTypes(GeometricField<Type, fvPatchField, volMesh>& fld)
 {
-    auto& fldBf = fld.boundaryFieldRef();
+    auto& bfld = fld.boundaryFieldRef();
 
     const UPstream::commsTypes commsType = UPstream::defaultCommsType;
-    const label startOfRequests = UPstream::nRequests();
 
     if
     (
@@ -52,37 +51,32 @@ void evaluateConstraintTypes(GeometricField<Type, fvPatchField, volMesh>& fld)
      || commsType == UPstream::commsTypes::nonBlocking
     )
     {
-        forAll(fldBf, patchi)
-        {
-            fvPatchField<Type>& tgtField = fldBf[patchi];
+        const label startOfRequests = UPstream::nRequests();
 
+        for (auto& pfld : bfld)
+        {
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
-                tgtField.initEvaluate(commsType);
+                pfld.initEvaluate(commsType);
             }
         }
 
-        // Wait for outstanding requests
-        if (commsType == UPstream::commsTypes::nonBlocking)
-        {
-            UPstream::waitRequests(startOfRequests);
-        }
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
 
-        forAll(fldBf, patchi)
+        for (auto& pfld : bfld)
         {
-            fvPatchField<Type>& tgtField = fldBf[patchi];
-
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
-                tgtField.evaluate(commsType);
+                pfld.evaluate(commsType);
             }
         }
     }
@@ -94,22 +88,21 @@ void evaluateConstraintTypes(GeometricField<Type, fvPatchField, volMesh>& fld)
         for (const auto& schedEval : patchSchedule)
         {
             const label patchi = schedEval.patch;
-
-            fvPatchField<Type>& tgtField = fldBf[patchi];
+            auto& pfld = bfld[patchi];
 
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
                 if (schedEval.init)
                 {
-                    tgtField.initEvaluate(commsType);
+                    pfld.initEvaluate(commsType);
                 }
                 else
                 {
-                    tgtField.evaluate(commsType);
+                    pfld.evaluate(commsType);
                 }
             }
         }
diff --git a/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedField.H b/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedField.H
index e7b4d21c6f1fe307095b40c3e89d5dfcc5f848c1..d37b651781dfd0aad851079901e4f1378d472397 100644
--- a/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedField.H
+++ b/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedField.H
@@ -115,8 +115,12 @@ private:
         //- Assert that non-zero field size == mesh size
         void checkFieldSize() const;
 
+        //- Read from file if it is present. Checks the readOption flag
         void readIfPresent(const word& fieldDictEntry = "value");
 
+        //- Read the field - create the field dictionary on-the-fly
+        void readField(const word& fieldDictEntry = "value");
+
         //- Implementation for 'New' with specified registerObject preference.
         //  For LEGACY_REGISTER, registration is determined by
         //  objectRegistry::is_cacheTemporaryObject().
@@ -580,8 +584,8 @@ public:
         bool writeData(Ostream& os, const word& fieldDictEntry) const;
 
         //- The writeData function (required by regIOobject),
-        //- call writeData with dictionary entry name = "value"
-        bool writeData(Ostream& os) const;
+        //- calls writeData with dictionary entry name = "value"
+        bool writeData(Ostream& os) const { return writeData(os, "value"); }
 
 
     // Member Operators
@@ -613,12 +617,14 @@ public:
 
     // Ostream Operators
 
+        //- Calls DimensionedField::writeData()
         friend Ostream& operator<< <Type, GeoMesh>
         (
             Ostream& os,
             const DimensionedField<Type, GeoMesh>& df
         );
 
+        //- Calls DimensionedField::writeData()
         friend Ostream& operator<< <Type, GeoMesh>
         (
             Ostream& os,
diff --git a/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedFieldIO.C b/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedFieldIO.C
index 57a0da9e6649de7dd7d3b07d129933b5cda375a5..7ad8544616f189d840088cb894cdf0a39fe628ac 100644
--- a/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedFieldIO.C
+++ b/src/OpenFOAM/fields/DimensionedFields/DimensionedField/DimensionedFieldIO.C
@@ -28,6 +28,7 @@ License
 
 #include "DimensionedField.H"
 #include "IOstreams.H"
+#include "localIOdictionary.H"
 
 // * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
 
@@ -58,15 +59,49 @@ void Foam::DimensionedField<Type, GeoMesh>::readField
 }
 
 
+template<class Type, class GeoMesh>
+void Foam::DimensionedField<Type, GeoMesh>::readField
+(
+    const word& fieldDictEntry
+)
+{
+    dictionary dict
+    (
+        localIOdictionary::readContents
+        (
+            IOobject
+            (
+                this->name(),
+                this->instance(),
+                this->local(),
+                this->db(),
+                IOobjectOption::MUST_READ,
+                IOobjectOption::NO_WRITE,
+                IOobjectOption::NO_REGISTER
+            ),
+            typeName
+        )
+    );
+
+    this->close();
+
+    readField(dict, fieldDictEntry);
+}
+
+
 template<class Type, class GeoMesh>
 void Foam::DimensionedField<Type, GeoMesh>::readIfPresent
 (
     const word& fieldDictEntry
 )
 {
-    if (this->isReadRequired() || (this->isReadOptional() && this->headerOk()))
+    if
+    (
+        this->isReadRequired()
+     || (this->isReadOptional() && this->headerOk())
+    )
     {
-        readField(dictionary(readStream(typeName)), fieldDictEntry);
+        readField(fieldDictEntry);
     }
 }
 
@@ -87,7 +122,7 @@ Foam::DimensionedField<Type, GeoMesh>::DimensionedField
     dimensions_(dimless),
     oriented_()
 {
-    readField(dictionary(readStream(typeName)), fieldDictEntry);
+    readField(fieldDictEntry);
 }
 
 
@@ -134,23 +169,16 @@ bool Foam::DimensionedField<Type, GeoMesh>::writeData
 }
 
 
-template<class Type, class GeoMesh>
-bool Foam::DimensionedField<Type, GeoMesh>::writeData(Ostream& os) const
-{
-    return writeData(os, "value");
-}
-
-
 // * * * * * * * * * * * * * * * IOstream Operators  * * * * * * * * * * * * //
 
 template<class Type, class GeoMesh>
 Foam::Ostream& Foam::operator<<
 (
     Ostream& os,
-    const DimensionedField<Type, GeoMesh>& df
+    const DimensionedField<Type, GeoMesh>& fld
 )
 {
-    df.writeData(os);
+    fld.writeData(os);
 
     return os;
 }
@@ -160,11 +188,11 @@ template<class Type, class GeoMesh>
 Foam::Ostream& Foam::operator<<
 (
     Ostream& os,
-    const tmp<DimensionedField<Type, GeoMesh>>& tdf
+    const tmp<DimensionedField<Type, GeoMesh>>& tfld
 )
 {
-    tdf().writeData(os);
-    tdf.clear();
+    tfld().writeData(os);
+    tfld.clear();
 
     return os;
 }
diff --git a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.C b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.C
index 70d5ce25560fbebf59db57104610446c48f3a6e2..aff9204eefe4ae764c2de34454293b1841182d52 100644
--- a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.C
+++ b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.C
@@ -91,7 +91,7 @@ bool Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::checkConsistency
             }
         }
 
-        // Wait for outstanding requests
+        // Wait for outstanding requests (non-blocking)
         UPstream::waitRequests(startOfRequests);
 
         for (auto& pfld : bfld)
@@ -193,10 +193,7 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::readField
     const dictionary& dict
 )
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     // Clear the boundary field if already initialised
     this->clear();
@@ -363,10 +360,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
     FieldField<PatchField, Type>(bmesh.size()),
     bmesh_(bmesh)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     forAll(bmesh_, patchi)
     {
@@ -396,10 +390,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
     FieldField<PatchField, Type>(bmesh.size()),
     bmesh_(bmesh)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     if
     (
@@ -462,10 +453,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
     FieldField<PatchField, Type>(bmesh.size()),
     bmesh_(bmesh)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     forAll(bmesh_, patchi)
     {
@@ -484,10 +472,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
     FieldField<PatchField, Type>(btf.size()),
     bmesh_(btf.bmesh_)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     forAll(bmesh_, patchi)
     {
@@ -508,10 +493,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
     FieldField<PatchField, Type>(btf.size()),
     bmesh_(btf.bmesh_)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     for (const label patchi : patchIDs)
     {
@@ -545,12 +527,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
 :
     FieldField<PatchField, Type>(btf),
     bmesh_(btf.bmesh_)
-{
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
-}
+{}
 
 
 template<class Type, template<class> class PatchField, class GeoMesh>
@@ -573,10 +550,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::GeometricBoundaryField
 template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::updateCoeffs()
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     for (auto& pfld : *this)
     {
@@ -586,32 +560,26 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::updateCoeffs()
 
 
 template<class Type, template<class> class PatchField, class GeoMesh>
-void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluate()
+void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluate
+(
+    const UPstream::commsTypes commsType
+)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
-
-    const UPstream::commsTypes commsType = UPstream::defaultCommsType;
-    const label startOfRequests = UPstream::nRequests();
-
     if
     (
         commsType == UPstream::commsTypes::buffered
      || commsType == UPstream::commsTypes::nonBlocking
     )
     {
+        const label startOfRequests = UPstream::nRequests();
+
         for (auto& pfld : *this)
         {
             pfld.initEvaluate(commsType);
         }
 
-        // Wait for outstanding requests
-        if (commsType == Pstream::commsTypes::nonBlocking)
-        {
-            UPstream::waitRequests(startOfRequests);
-        }
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
 
         for (auto& pfld : *this)
         {
@@ -641,8 +609,74 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluate()
     else
     {
         FatalErrorInFunction
-            << "Unsupported communications type "
-            << UPstream::commsTypeNames[commsType]
+            << "Unsupported communications type " << int(commsType) << nl
+            << exit(FatalError);
+    }
+}
+
+
+template<class Type, template<class> class PatchField, class GeoMesh>
+template<class UnaryPredicate>
+void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluate_if
+(
+    const UnaryPredicate& pred,
+    const UPstream::commsTypes commsType
+)
+{
+    if
+    (
+        commsType == UPstream::commsTypes::buffered
+     || commsType == UPstream::commsTypes::nonBlocking
+    )
+    {
+        const label startOfRequests = UPstream::nRequests();
+
+        for (auto& pfld : *this)
+        {
+            if (pred(pfld))
+            {
+                pfld.initEvaluate(commsType);
+            }
+        }
+
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
+
+        for (auto& pfld : *this)
+        {
+            if (pred(pfld))
+            {
+                pfld.evaluate(commsType);
+            }
+        }
+    }
+    else if (commsType == UPstream::commsTypes::scheduled)
+    {
+        const lduSchedule& patchSchedule =
+            bmesh_.mesh().globalData().patchSchedule();
+
+        for (const auto& schedEval : patchSchedule)
+        {
+            const label patchi = schedEval.patch;
+            auto& pfld = (*this)[patchi];
+
+            if (pred(pfld))
+            {
+                if (schedEval.init)
+                {
+                    pfld.initEvaluate(commsType);
+                }
+                else
+                {
+                    pfld.evaluate(commsType);
+                }
+            }
+        }
+    }
+    else
+    {
+        FatalErrorInFunction
+            << "Unsupported communications type " << int(commsType) << nl
             << exit(FatalError);
     }
 }
@@ -651,58 +685,60 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluate()
 template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateSelected
 (
-    const UList<label>& patchIDs
+    const labelUList& patchIDs
 )
 {
+    const label startOfRequests = UPstream::nRequests();
+
     for (const label patchi : patchIDs)
     {
-        auto& pf = (*this)[patchi];
+        auto& pfld = (*this)[patchi];
 
-        DebugInfo<< "Updating " << pf.patch().name() << endl;
+        DebugInfo<< "Updating " << pfld.patch().name() << endl;
 
-        const label startOfRequests = UPstream::nRequests();
+        pfld.initEvaluate(UPstream::commsTypes::nonBlocking);
+    }
 
-        pf.initEvaluate(UPstream::commsTypes::nonBlocking);
+    // Wait for outstanding requests (non-blocking)
+    UPstream::waitRequests(startOfRequests);
 
-        UPstream::waitRequests(startOfRequests);
+    for (const label patchi : patchIDs)
+    {
+        auto& pfld = (*this)[patchi];
 
-        pf.evaluate(UPstream::commsTypes::nonBlocking);
+        pfld.evaluate(UPstream::commsTypes::nonBlocking);
     }
 }
 
 
 template<class Type, template<class> class PatchField, class GeoMesh>
-void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateLocal()
+void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateLocal
+(
+    const UPstream::commsTypes commsType
+)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
+    // DebugInFunction << nl;
 
     if (!localConsistency)
     {
         return;
     }
 
-    const UPstream::commsTypes commsType = UPstream::defaultCommsType;
-    const label startOfRequests = UPstream::nRequests();
-
     if
     (
         commsType == UPstream::commsTypes::buffered
      || commsType == UPstream::commsTypes::nonBlocking
     )
     {
+        const label startOfRequests = UPstream::nRequests();
+
         for (auto& pfld : *this)
         {
             pfld.initEvaluateLocal(commsType);
         }
 
-        // Wait for outstanding requests
-        if (commsType == Pstream::commsTypes::nonBlocking)
-        {
-            UPstream::waitRequests(startOfRequests);
-        }
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
 
         for (auto& pfld : *this)
         {
@@ -732,8 +768,7 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateLocal()
     else
     {
         FatalErrorInFunction
-            << "Unsupported communications type "
-            << UPstream::commsTypeNames[commsType]
+            << "Unsupported communications type " << int(commsType) << nl
             << exit(FatalError);
     }
 }
@@ -741,17 +776,24 @@ void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateLocal()
 
 template<class Type, template<class> class PatchField, class GeoMesh>
 template<class CoupledPatchType>
-void
-Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>
-::evaluateCoupled()
+void Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>::evaluateCoupled
+(
+    const UPstream::commsTypes commsType
+)
 {
-    ///if (GeometricField<Type, PatchField, GeoMesh::debug)
-    ///{
-    ///    InfoInFunction << nl;
-    ///}
-
-    const UPstream::commsTypes commsType = UPstream::defaultCommsType;
-    const label startOfRequests = UPstream::nRequests();
+    // Alternative (C++14)
+    //
+    // this->evaluate_if
+    // (
+    //     [](const auto& pfld) -> bool
+    //     {
+    //         const auto* cpp = isA<CoupledPatchType>(pfld.patch());
+    //         return (cpp && cpp->coupled());
+    //     },
+    //     commsType
+    // );
+
+    // DebugInFunction << nl;
 
     if
     (
@@ -759,6 +801,8 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>
      || commsType == UPstream::commsTypes::nonBlocking
     )
     {
+        const label startOfRequests = UPstream::nRequests();
+
         for (auto& pfld : *this)
         {
             const auto* cpp = isA<CoupledPatchType>(pfld.patch());
@@ -769,11 +813,8 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>
             }
         }
 
-        // Wait for outstanding requests
-        if (commsType == UPstream::commsTypes::nonBlocking)
-        {
-            UPstream::waitRequests(startOfRequests);
-        }
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
 
         for (auto& pfld : *this)
         {
@@ -813,8 +854,7 @@ Foam::GeometricBoundaryField<Type, PatchField, GeoMesh>
     else
     {
         FatalErrorInFunction
-            << "Unsupported communications type "
-            << UPstream::commsTypeNames[commsType]
+            << "Unsupported communications type " << int(commsType) << nl
             << exit(FatalError);
     }
 }
diff --git a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.H b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.H
index 3e327184099500bcfb3a10758f96e2ab8e15ba10..28834c39ced55b7317e30824cca3e1c41c80a404 100644
--- a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.H
+++ b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricBoundaryField.H
@@ -6,7 +6,7 @@
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
     Copyright (C) 2011-2017,2022 OpenFOAM Foundation
-    Copyright (C) 2015-2023 OpenCFD Ltd.
+    Copyright (C) 2015-2024 OpenCFD Ltd.
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -49,12 +49,6 @@ SourceFiles
 namespace Foam
 {
 
-// Forward Declarations
-class dictionary;
-
-template<class Type, template<class> class PatchField, class GeoMesh>
-class GeometricField;
-
 /*---------------------------------------------------------------------------*\
                    Class GeometricBoundaryField Declaration
 \*---------------------------------------------------------------------------*/
@@ -74,6 +68,9 @@ public:
         //- The internal field type associated with the boundary fields
         typedef DimensionedField<Type, GeoMesh> Internal;
 
+        //- This boundary field type
+        typedef GeometricBoundaryField<Type, PatchField, GeoMesh> Boundary;
+
         //- The patch field type for the boundary fields
         typedef PatchField<Type> Patch;
 
@@ -182,18 +179,40 @@ public:
         //- Update the boundary condition coefficients
         void updateCoeffs();
 
-        //- Evaluate boundary conditions
-        void evaluate();
+        //- Evaluate boundary conditions for each patch field.
+        //- Uses specified or default comms.
+        void evaluate
+        (
+            const UPstream::commsTypes commsType = UPstream::defaultCommsType
+        );
 
-        //- Evaluate boundary conditions after change in local values
-        void evaluateLocal();
+        //- Evaluate boundary conditions for patch fields matching the
+        //- given predicate. Uses specified or default comms.
+        template<class UnaryPredicate>
+        void evaluate_if
+        (
+            const UnaryPredicate& pred,
+            const UPstream::commsTypes commsType = UPstream::defaultCommsType
+        );
+
+        //- Evaluate boundary conditions after change in local values.
+        //- Uses specified or default comms.
+        void evaluateLocal
+        (
+            const UPstream::commsTypes commsType = UPstream::defaultCommsType
+        );
 
-        //- Evaluate boundary conditions on a subset of coupled patches
+        //- Evaluate boundary conditions on coupled patches of given type.
+        //- Uses specified or default comms.
         template<class CoupledPatchType>
-        void evaluateCoupled();
+        void evaluateCoupled
+        (
+            const UPstream::commsTypes commsType = UPstream::defaultCommsType
+        );
 
-        //- Evaluate boundary conditions for selected patches
-        void evaluateSelected(const UList<label>& patchIDs);
+        //- Evaluate boundary conditions for selected patches.
+        //- Uses non-blocking comms.
+        void evaluateSelected(const labelUList& patchIDs);
 
         //- Return a list of the patch types
         wordList types() const;
@@ -209,15 +228,18 @@ public:
         //- pointing to interfaces being set
         lduInterfaceFieldPtrsList scalarInterfaces() const;
 
+        //- Helper: check if field has been evaluated. See instantiations.
+        bool check() const;
+
+
+    // Write
+
         //- Write boundary field as dictionary entry
         void writeEntry(const word& keyword, Ostream& os) const;
 
         //- Write dictionary entries of the individual boundary fields.
         void writeEntries(Ostream& os) const;
 
-        //- Helper: check if field has been evaluated. See instantiations.
-        bool check() const;
-
 
     // Member Operators
 
diff --git a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.C b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.C
index 12603e72ef574c80369496e50065e453a082974f..2ec59ff2d74d319d99e8c85d94afd55cd79e48d0 100644
--- a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.C
+++ b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.C
@@ -6,7 +6,7 @@
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
     Copyright (C) 2011-2017 OpenFOAM Foundation
-    Copyright (C) 2015-2023 OpenCFD Ltd.
+    Copyright (C) 2015-2024 OpenCFD Ltd.
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -28,7 +28,6 @@ License
 
 #include "GeometricField.H"
 #include "Time.H"
-#include "demandDrivenData.H"
 #include "dictionary.H"
 #include "localIOdictionary.H"
 #include "meshState.H"
@@ -77,19 +76,22 @@ void Foam::GeometricField<Type, PatchField, GeoMesh>::readFields
 template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricField<Type, PatchField, GeoMesh>::readFields()
 {
-    const localIOdictionary dict
+    dictionary dict
     (
-        IOobject
+        localIOdictionary::readContents
         (
-            this->name(),
-            this->instance(),
-            this->local(),
-            this->db(),
-            IOobjectOption::MUST_READ,
-            IOobjectOption::NO_WRITE,
-            IOobjectOption::NO_REGISTER
-        ),
-        typeName
+            IOobject
+            (
+                this->name(),
+                this->instance(),
+                this->local(),
+                this->db(),
+                IOobjectOption::MUST_READ,
+                IOobjectOption::NO_WRITE,
+                IOobjectOption::NO_REGISTER
+            ),
+            typeName
+        )
     );
 
     this->close();
@@ -111,10 +113,7 @@ bool Foam::GeometricField<Type, PatchField, GeoMesh>::readIfPresent()
     else if
     (
         this->isReadOptional()
-     && this->template typeHeaderOk<GeometricField<Type, PatchField, GeoMesh>>
-        (
-            true
-        )
+     && this->template typeHeaderOk<this_type>(true)  // checkType = true
     )
     {
         readFields();
@@ -143,20 +142,13 @@ bool Foam::GeometricField<Type, PatchField, GeoMesh>::readOldTimeIfPresent()
 
     if
     (
-        field0.template typeHeaderOk<GeometricField<Type, PatchField, GeoMesh>>
-        (
-            true
-        )
+        field0.template typeHeaderOk<this_type>(true)  // checkType = true
     )
     {
         DebugInFunction
             << "Reading old time level for field" << nl << this->info() << endl;
 
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
-        (
-            field0,
-            this->mesh()
-        );
+        field0Ptr_ = std::make_unique<this_type>(field0, this->mesh());
 
         // Ensure the old time field oriented flag is set to the parent's state
         // Note: required for backwards compatibility in case of restarting from
@@ -190,8 +182,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldType)
 {
     DebugInFunction
@@ -213,8 +203,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldTypes, actualPatchTypes)
 {
     DebugInFunction
@@ -236,8 +224,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, value, dims, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldType)
 {
     DebugInFunction
@@ -262,8 +248,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, value, dims, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldTypes, actualPatchTypes)
 {
     DebugInFunction
@@ -327,8 +311,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, diField),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -348,8 +330,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, std::move(diField)),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -369,8 +349,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, tfield),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -389,8 +367,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(diField),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -409,8 +385,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(std::move(diField)),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -432,8 +406,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, iField),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldType)
 {
     DebugInFunction
@@ -455,8 +427,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, std::move(iField)),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, patchFieldType)
 {
     DebugInFunction
@@ -478,8 +448,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, iField),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -501,8 +469,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, std::move(iField)),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -524,8 +490,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dims, tfield),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary(), *this, ptfl)
 {
     DebugInFunction
@@ -545,8 +509,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dimless, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary())
 {
     DebugInFunction
@@ -584,8 +546,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, mesh, dimless, false),
     timeIndex_(this->time().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(mesh.boundary())
 {
     readFields(dict);
@@ -603,8 +563,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, gf.boundaryField_)
 {
     DebugInFunction
@@ -612,10 +570,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
-        (
-            *gf.field0Ptr_
-        );
+        field0Ptr_ = std::make_unique<this_type>(*gf.field0Ptr_);
     }
 
     this->writeOpt(IOobjectOption::NO_WRITE);
@@ -630,8 +585,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(tgf.constCast(), tgf.movable()),
     timeIndex_(tgf().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, tgf().boundaryField_)
 {
     DebugInFunction
@@ -652,8 +605,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, gf.boundaryField_)
 {
     DebugInFunction
@@ -662,7 +613,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (!readIfPresent() && gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             io.name() + "_0",
             *gf.field0Ptr_
@@ -680,8 +631,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, tgf.constCast(), tgf.movable()),
     timeIndex_(tgf().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, tgf().boundaryField_)
 {
     DebugInFunction
@@ -703,8 +652,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(newName, gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, gf.boundaryField_)
 {
     DebugInFunction
@@ -713,7 +660,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (!readIfPresent() && gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             newName + "_0",
             *gf.field0Ptr_
@@ -731,8 +678,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(newName, tgf.constCast(), tgf.movable()),
     timeIndex_(tgf().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, tgf().boundaryField_)
 {
     DebugInFunction
@@ -753,8 +698,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(this->mesh().boundary(), *this, patchFieldType)
 {
     DebugInFunction
@@ -765,7 +708,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (!readIfPresent() && gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             io.name() + "_0",
             *gf.field0Ptr_
@@ -785,8 +728,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_
     (
         this->mesh().boundary(),
@@ -803,7 +744,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (!readIfPresent() && gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             io.name() + "_0",
             *gf.field0Ptr_
@@ -823,8 +764,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, gf),
     timeIndex_(gf.timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_(*this, gf.boundaryField_, patchIDs, patchFieldType)
 {
     DebugInFunction
@@ -834,7 +773,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 
     if (!readIfPresent() && gf.field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             io.name() + "_0",
             *gf.field0Ptr_
@@ -854,8 +793,6 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::GeometricField
 :
     Internal(io, tgf.constCast(), tgf.movable()),
     timeIndex_(tgf().timeIndex()),
-    field0Ptr_(nullptr),
-    fieldPrevIterPtr_(nullptr),
     boundaryField_
     (
         this->mesh().boundary(),
@@ -897,13 +834,8 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::~GeometricField()
     }
     */
 
-    deleteDemandDrivenData(field0Ptr_);
-    deleteDemandDrivenData(fieldPrevIterPtr_);
-
     // FUTURE: register cache field info
     // // this->db().cacheTemporaryObject(*this);
-
-    clearOldTimes();
 }
 
 
@@ -1014,7 +946,7 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::oldTime() const
 {
     if (!field0Ptr_)
     {
-        field0Ptr_ = new GeometricField<Type, PatchField, GeoMesh>
+        field0Ptr_ = std::make_unique<this_type>
         (
             IOobject
             (
@@ -1068,7 +1000,7 @@ void Foam::GeometricField<Type, PatchField, GeoMesh>::storePrevIter() const
             << "Allocating previous iteration field" << nl
             << this->info() << endl;
 
-        fieldPrevIterPtr_ = new GeometricField<Type, PatchField, GeoMesh>
+        fieldPrevIterPtr_ = std::make_unique<this_type>
         (
             this->name() + "PrevIter",
             *this
@@ -1101,8 +1033,8 @@ Foam::GeometricField<Type, PatchField, GeoMesh>::prevIter() const
 template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricField<Type, PatchField, GeoMesh>::clearOldTimes()
 {
-    deleteDemandDrivenData(field0Ptr_);
-    deleteDemandDrivenData(fieldPrevIterPtr_);
+    field0Ptr_.reset(nullptr);
+    fieldPrevIterPtr_.reset(nullptr);
 }
 
 
@@ -1110,8 +1042,11 @@ template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricField<Type, PatchField, GeoMesh>::
 correctBoundaryConditions()
 {
-    this->setUpToDate();
-    storeOldTimes();
+    // updateAccessTime
+    {
+        this->setUpToDate();
+        storeOldTimes();
+    }
     boundaryField_.evaluate();
 }
 
@@ -1120,8 +1055,11 @@ template<class Type, template<class> class PatchField, class GeoMesh>
 void Foam::GeometricField<Type, PatchField, GeoMesh>::
 correctLocalBoundaryConditions()
 {
-    this->setUpToDate();
-    storeOldTimes();
+    // updateAccessTime
+    {
+        this->setUpToDate();
+        storeOldTimes();
+    }
     boundaryField_.evaluateLocal();
 }
 
@@ -1208,7 +1146,11 @@ template<class Type, template<class> class PatchField, class GeoMesh>
 bool Foam::GeometricField<Type, PatchField, GeoMesh>::
 writeData(Ostream& os) const
 {
-    os << *this;
+    this->internalField().writeData(os, "internalField");
+    os  << nl;
+    this->boundaryField().writeEntry("boundaryField", os);
+
+    os.check(FUNCTION_NAME);
     return os.good();
 }
 
@@ -1540,14 +1482,10 @@ template<class Type, template<class> class PatchField, class GeoMesh>
 Foam::Ostream& Foam::operator<<
 (
     Ostream& os,
-    const GeometricField<Type, PatchField, GeoMesh>& gf
+    const GeometricField<Type, PatchField, GeoMesh>& fld
 )
 {
-    gf.internalField().writeData(os, "internalField");
-    os  << nl;
-    gf.boundaryField().writeEntry("boundaryField", os);
-
-    os.check(FUNCTION_NAME);
+    fld.writeData(os);
     return os;
 }
 
@@ -1556,11 +1494,12 @@ template<class Type, template<class> class PatchField, class GeoMesh>
 Foam::Ostream& Foam::operator<<
 (
     Ostream& os,
-    const tmp<GeometricField<Type, PatchField, GeoMesh>>& tgf
+    const tmp<GeometricField<Type, PatchField, GeoMesh>>& tfld
 )
 {
-    os << tgf();
-    tgf.clear();
+    tfld().writeData(os);
+    tfld.clear();
+
     return os;
 }
 
diff --git a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.H b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.H
index 427009b24553d991fa9a8b6ef43ee9ed63364156..8cb500f580c66c083ae5201e21e4cb0f533f9a21 100644
--- a/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.H
+++ b/src/OpenFOAM/fields/GeometricFields/GeometricField/GeometricField.H
@@ -41,7 +41,6 @@ SourceFiles
 #ifndef Foam_GeometricField_H
 #define Foam_GeometricField_H
 
-#include "regIOobject.H"
 #include "GeometricBoundaryField.H"
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@@ -50,7 +49,6 @@ namespace Foam
 {
 
 // Forward Declarations
-class dictionary;
 
 template<class Type, template<class> class PatchField, class GeoMesh>
 class GeometricField;
@@ -104,6 +102,12 @@ public:
 
 private:
 
+    // Private Typedefs
+
+        //- The GeometricField type
+        typedef GeometricField<Type, PatchField, GeoMesh> this_type;
+
+
     // Private Data
 
         //- Current time index.
@@ -111,10 +115,10 @@ private:
         mutable label timeIndex_;
 
         //- Pointer to old time field
-        mutable GeometricField<Type, PatchField, GeoMesh>* field0Ptr_;
+        mutable std::unique_ptr<this_type> field0Ptr_;
 
         //- Pointer to previous iteration (used for under-relaxation)
-        mutable GeometricField<Type, PatchField, GeoMesh>* fieldPrevIterPtr_;
+        mutable std::unique_ptr<this_type> fieldPrevIterPtr_;
 
         //- Boundary field containing boundary field values
         Boundary boundaryField_;
@@ -871,8 +875,8 @@ public:
         //- Correct boundary field
         void correctBoundaryConditions();
 
-        //- Correct boundary conditions after a purely local operation. Is
-        //  dummy for e.g. processor boundary conditions
+        //- Correct boundary conditions after a purely local operation.
+        //  Is dummy for processor boundary conditions etc
         void correctLocalBoundaryConditions();
 
         //- Does the field need a reference level for solution
@@ -1008,19 +1012,20 @@ public:
 
     // Write
 
-        //- The writeData function (required by regIOobject),
-        //- calls operator<<
+        //- The writeData function (required by regIOobject)
         bool writeData(Ostream& os) const;
 
 
     // Ostream Operators
 
+        //- Calls GeometricField::writeData()
         friend Ostream& operator<< <Type, PatchField, GeoMesh>
         (
             Ostream&,
             const GeometricField<Type, PatchField, GeoMesh>&
         );
 
+        //- Calls GeometricField::writeData()
         friend Ostream& operator<< <Type, PatchField, GeoMesh>
         (
             Ostream&,
diff --git a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.C b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.C
index f7332a19006d8de98228e305f65a07eb5dea63ba..5d096e36f6ad1e91c02e9dfc89630fe083472829 100644
--- a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.C
+++ b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.C
@@ -1440,7 +1440,7 @@ void Foam::polyBoundaryMesh::writeEntry(Ostream& os) const
 
 void Foam::polyBoundaryMesh::writeEntry
 (
-    const keyType& keyword,
+    const word& keyword,
     Ostream& os
 ) const
 {
diff --git a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.H b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.H
index 93a059a06e61a5f47475135c80e7130d87d82284..d21d9cf0b59d7ea8f27cab3bb22056acd521fc5a 100644
--- a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.H
+++ b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMesh.H
@@ -379,7 +379,7 @@ public:
 
         //- Write as a primitive entry with given name.
         //- If the keyword is empty, revert to a plain list.
-        void writeEntry(const keyType& keyword, Ostream& os) const;
+        void writeEntry(const word& keyword, Ostream& os) const;
 
         //- The writeData member function required by regIOobject
         virtual bool writeData(Ostream& os) const;
diff --git a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.C b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.C
index 7cf2f53abb979b481dbe764ba12857943348cf39..e8c4cfe61c5a92f1dc1919f77d4bc6d8094c2fe4 100644
--- a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.C
+++ b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.C
@@ -214,7 +214,7 @@ void Foam::polyBoundaryMeshEntries::writeEntry(Ostream& os) const
 
 void Foam::polyBoundaryMeshEntries::writeEntry
 (
-    const keyType& keyword,
+    const word& keyword,
     Ostream& os
 ) const
 {
diff --git a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.H b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.H
index 2fb5c6feae2e6c20d52267ebe46ab52df0192843..e614c0929ab954516382dc93d350a16e06dbbeab 100644
--- a/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.H
+++ b/src/OpenFOAM/meshes/polyMesh/polyBoundaryMesh/polyBoundaryMeshEntries.H
@@ -121,7 +121,7 @@ public:
 
         //- Write as a primitive entry with given name.
         //- If the keyword is empty, revert to a plain list.
-        void writeEntry(const keyType& keyword, Ostream& os) const;
+        void writeEntry(const word& keyword, Ostream& os) const;
 
         //- The writeData member function required by regIOobject
         virtual bool writeData(Ostream& os) const;
diff --git a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.C b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.C
index 55ee4b2899a70a3f16aae2ee07e9575dfd4072de..e770328a70b77a713b826b51ff1cf40ead88dd1f 100644
--- a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.C
+++ b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.C
@@ -1058,7 +1058,7 @@ void Foam::faBoundaryMesh::writeEntry(Ostream& os) const
 
 void Foam::faBoundaryMesh::writeEntry
 (
-    const keyType& keyword,
+    const word& keyword,
     Ostream& os
 ) const
 {
diff --git a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.H b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.H
index 9c3cc9d0e90adb36263380cce30af8f7ae29858d..cad29247915e041c506a2ea9db56275d344cd336 100644
--- a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.H
+++ b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMesh.H
@@ -299,7 +299,7 @@ public:
 
         //- Write as a primitive entry with given name.
         //- If the keyword is empty, revert to a plain list.
-        void writeEntry(const keyType& keyword, Ostream& os) const;
+        void writeEntry(const word& keyword, Ostream& os) const;
 
         //- The writeData member function required by regIOobject
         virtual bool writeData(Ostream& os) const;
diff --git a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.C b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.C
index 59ebacfe33feb11bbc4d7f8a8e06e404f18cbd38..2a07f2fd997b49a768d83fe3ecb184e45d88e7fb 100644
--- a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.C
+++ b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.C
@@ -183,7 +183,7 @@ void Foam::faBoundaryMeshEntries::writeEntry(Ostream& os) const
 
 void Foam::faBoundaryMeshEntries::writeEntry
 (
-    const keyType& keyword,
+    const word& keyword,
     Ostream& os
 ) const
 {
diff --git a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.H b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.H
index c9f85716937e581ed05b988658c3216e56483ae3..ccaebe01acc4b4db6e58454758241e92e6f91bd5 100644
--- a/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.H
+++ b/src/finiteArea/faMesh/faBoundaryMesh/faBoundaryMeshEntries.H
@@ -108,7 +108,7 @@ public:
 
         //- Write as a primitive entry with given name.
         //- If the keyword is empty, revert to a plain list.
-        void writeEntry(const keyType& keyword, Ostream& os) const;
+        void writeEntry(const word& keyword, Ostream& os) const;
 
         //- The writeData member function required by regIOobject
         virtual bool writeData(Ostream& os) const;
diff --git a/src/finiteVolume/interpolation/volPointInterpolation/volPointInterpolate.C b/src/finiteVolume/interpolation/volPointInterpolation/volPointInterpolate.C
index 3ef984cf4d7329e1da468bd4bd5dd08c86ed9702..f1b7fd0ff0a27eb1a8f29f314649a29d2926cbd3 100644
--- a/src/finiteVolume/interpolation/volPointInterpolation/volPointInterpolate.C
+++ b/src/finiteVolume/interpolation/volPointInterpolation/volPointInterpolate.C
@@ -107,8 +107,7 @@ void Foam::volPointInterpolation::addSeparated
         }
     }
 
-    // Wait for outstanding requests
-    // (commsType == UPstream::commsTypes::nonBlocking)
+    // Wait for outstanding requests (non-blocking)
     UPstream::waitRequests(startOfRequests);
 
     forAll(pfbf, patchi)
diff --git a/src/functionObjects/field/mapFields/mapFieldsTemplates.C b/src/functionObjects/field/mapFields/mapFieldsTemplates.C
index 2350ef32c0e4ed4ea60b3b81fc77fc568555e281..58bd9572dca488982ca429b71baf34e292690d9e 100644
--- a/src/functionObjects/field/mapFields/mapFieldsTemplates.C
+++ b/src/functionObjects/field/mapFields/mapFieldsTemplates.C
@@ -36,10 +36,9 @@ void Foam::functionObjects::mapFields::evaluateConstraintTypes
     GeometricField<Type, fvPatchField, volMesh>& fld
 ) const
 {
-    auto& fldBf = fld.boundaryFieldRef();
+    auto& bfld = fld.boundaryFieldRef();
 
     const UPstream::commsTypes commsType = UPstream::defaultCommsType;
-    const label startOfRequests = UPstream::nRequests();
 
     if
     (
@@ -47,37 +46,32 @@ void Foam::functionObjects::mapFields::evaluateConstraintTypes
      || commsType == UPstream::commsTypes::nonBlocking
     )
     {
-        forAll(fldBf, patchi)
-        {
-            fvPatchField<Type>& tgtField = fldBf[patchi];
+        const label startOfRequests = UPstream::nRequests();
 
+        for (auto& pfld : bfld)
+        {
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
-                tgtField.initEvaluate(commsType);
+                pfld.initEvaluate(commsType);
             }
         }
 
-        // Wait for outstanding requests
-        if (commsType == UPstream::commsTypes::nonBlocking)
-        {
-            UPstream::waitRequests(startOfRequests);
-        }
+        // Wait for outstanding requests (non-blocking)
+        UPstream::waitRequests(startOfRequests);
 
-        forAll(fldBf, patchi)
+        for (auto& pfld : bfld)
         {
-            fvPatchField<Type>& tgtField = fldBf[patchi];
-
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
-                tgtField.evaluate(commsType);
+                pfld.evaluate(commsType);
             }
         }
     }
@@ -89,22 +83,21 @@ void Foam::functionObjects::mapFields::evaluateConstraintTypes
         for (const auto& schedEval : patchSchedule)
         {
             const label patchi = schedEval.patch;
-
-            fvPatchField<Type>& tgtField = fldBf[patchi];
+            auto& pfld = bfld[patchi];
 
             if
             (
-                tgtField.type() == tgtField.patch().patch().type()
-             && polyPatch::constraintType(tgtField.patch().patch().type())
+                pfld.type() == pfld.patch().patch().type()
+             && polyPatch::constraintType(pfld.patch().patch().type())
             )
             {
                 if (schedEval.init)
                 {
-                    tgtField.initEvaluate(commsType);
+                    pfld.initEvaluate(commsType);
                 }
                 else
                 {
-                    tgtField.evaluate(commsType);
+                    pfld.evaluate(commsType);
                 }
             }
         }
diff --git a/src/functionObjects/field/zeroGradient/zeroGradientTemplates.C b/src/functionObjects/field/zeroGradient/zeroGradientTemplates.C
index 0894b199d55e0d0d2d2c6a615a18648fa0afe9b7..0c6dcd4ecb9afa2e1b8898d978d367e59b569955 100644
--- a/src/functionObjects/field/zeroGradient/zeroGradientTemplates.C
+++ b/src/functionObjects/field/zeroGradient/zeroGradientTemplates.C
@@ -37,11 +37,9 @@ bool Foam::functionObjects::zeroGradient::accept
     const GeometricField<Type, fvPatchField, volMesh>& input
 )
 {
-    const auto& patches = input.boundaryField();
-
-    forAll(patches, patchi)
+    for (const auto& pfld : input.boundaryField())
     {
-        if (!polyPatch::constraintType(patches[patchi].patch().patch().type()))
+        if (!polyPatch::constraintType(pfld.patch().patch().type()))
         {
             return true;
         }
diff --git a/src/meshTools/topoSet/cellSources/fieldToCell/fieldDictionary.H b/src/meshTools/topoSet/cellSources/fieldToCell/fieldDictionary.H
index 999f5a8862c5f2bd8e2a9354a68fb2dedb517c01..c04f5bfb384fa65487ea2fd2855f54fa263e36e6 100644
--- a/src/meshTools/topoSet/cellSources/fieldToCell/fieldDictionary.H
+++ b/src/meshTools/topoSet/cellSources/fieldToCell/fieldDictionary.H
@@ -32,11 +32,11 @@ Description
 
 \*---------------------------------------------------------------------------*/
 
-#ifndef fieldDictionary_H
-#define fieldDictionary_H
+#ifndef Foam_fieldDictionary_H
+#define Foam_fieldDictionary_H
 
-#include "regIOobject.H"
 #include "dictionary.H"
+#include "regIOobject.H"
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
@@ -52,22 +52,22 @@ class fieldDictionary
     public regIOobject,
     public dictionary
 {
-
     // Private Data
 
-        const word type_;
+        //- The specified field type
+        const word fieldType_;
 
 
 public:
 
     // Constructors
 
-        //- Construct from ioobject and overloaded typename.
-        fieldDictionary(const IOobject& io, const word& type)
+        //- Construct from IOobject and specified (overloaded) type name
+        fieldDictionary(const IOobject& io, const word& fieldType)
         :
             regIOobject(io),
-            dictionary(readStream(type)),
-            type_(type)
+            dictionary(readStream(fieldType)),
+            fieldType_(fieldType)
         {
             close();
         }
@@ -78,13 +78,13 @@ public:
         //- Redefine type name to be of the instantiated type
         virtual const word& type() const
         {
-            return type_;
+            return fieldType_;
         }
 
-        bool writeData(Ostream& os) const
+        //- The writeData function required by regIOobject write operation
+        virtual bool writeData(Ostream& os) const
         {
-            static_cast<const dictionary&>(*this).write(os, false);
-
+            dictionary::write(os, false);
             return os.good();
         }
 };
diff --git a/src/overset/cellCellStencil/cellCellStencil/cellCellStencilTemplates.C b/src/overset/cellCellStencil/cellCellStencil/cellCellStencilTemplates.C
index 80237911108c8e90b10d9df3699f4a235f0c38f8..f110df646323b6ec8edfdf52b1d987708976f99c 100644
--- a/src/overset/cellCellStencil/cellCellStencil/cellCellStencilTemplates.C
+++ b/src/overset/cellCellStencil/cellCellStencil/cellCellStencilTemplates.C
@@ -185,29 +185,26 @@ void Foam::cellCellStencil::correctBoundaryConditions
     // Version of GeoField::correctBoundaryConditions that exclude evaluation
     // of oversetFvPatchFields
 
-    typename GeoField::Boundary& bfld = psi.boundaryFieldRef();
+    auto& bfld = psi.boundaryFieldRef();
 
-    const label nReq = Pstream::nRequests();
+    const label startOfRequests = UPstream::nRequests();
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (!isA<SuppressBC>(bfld[patchi]))
+        if (!isA<SuppressBC>(pfld))
         {
-            bfld[patchi].initEvaluate(Pstream::commsTypes::nonBlocking);
+            pfld.initEvaluate(UPstream::commsTypes::nonBlocking);
         }
     }
 
-    // Block for any outstanding requests
-    if (Pstream::parRun())
-    {
-        Pstream::waitRequests(nReq);
-    }
+    // Wait for outstanding requests (non-blocking)
+    UPstream::waitRequests(startOfRequests);
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (!isA<SuppressBC>(bfld[patchi]))
+        if (!isA<SuppressBC>(pfld))
         {
-            bfld[patchi].evaluate(Pstream::commsTypes::nonBlocking);
+            pfld.evaluate(UPstream::commsTypes::nonBlocking);
         }
     }
 }
diff --git a/src/overset/oversetFvMesh/oversetFvMeshBase.H b/src/overset/oversetFvMesh/oversetFvMeshBase.H
index 4951322195407967f1542ce710d892d10e4abaeb..b0678b1a24b4ec27483d9d39b2c049b6487be18a 100644
--- a/src/overset/oversetFvMesh/oversetFvMeshBase.H
+++ b/src/overset/oversetFvMesh/oversetFvMeshBase.H
@@ -256,7 +256,7 @@ public:
         static void checkCoupledBC(const GeoField& fld);
 
         //- Correct boundary conditions of certain type (typeOnly = true)
-        //  or explicitly not of the type (typeOnly = false)
+        //- or explicitly not of the type (typeOnly = false)
         template<class GeoField, class PatchType>
         static void correctBoundaryConditions
         (
diff --git a/src/overset/oversetFvMesh/oversetFvMeshBaseTemplates.C b/src/overset/oversetFvMesh/oversetFvMeshBaseTemplates.C
index c57a63581880f4fe96015ae4f73da1c748deca70..471cbee742facc2807b554ff4b78613c20321ac7 100644
--- a/src/overset/oversetFvMesh/oversetFvMeshBaseTemplates.C
+++ b/src/overset/oversetFvMesh/oversetFvMeshBaseTemplates.C
@@ -80,28 +80,36 @@ void Foam::oversetFvMeshBase::correctBoundaryConditions
     const bool typeOnly
 )
 {
+    // Alternative (C++14)
+    //
+    // bfld.evaluate_if
+    // (
+    //     [typeOnly](const auto& pfld) -> bool
+    //     {
+    //         return (typeOnly == bool(isA<PatchType>(pfld)));
+    //     },
+    //     UPstream::defaultCommsType
+    // );
+
     const UPstream::commsTypes commsType = UPstream::defaultCommsType;
     const label startOfRequests = UPstream::nRequests();
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (typeOnly == (isA<PatchType>(bfld[patchi]) != nullptr))
+        if (typeOnly == bool(isA<PatchType>(pfld)))
         {
-            bfld[patchi].initEvaluate(commsType);
+            pfld.initEvaluate(commsType);
         }
     }
 
-    // Wait for outstanding requests
-    if (commsType == UPstream::commsTypes::nonBlocking)
-    {
-        Pstream::waitRequests(startOfRequests);
-    }
+    // Wait for outstanding requests (non-blocking)
+    UPstream::waitRequests(startOfRequests);
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (typeOnly == (isA<PatchType>(bfld[patchi]) != nullptr))
+        if (typeOnly == bool(isA<PatchType>(pfld)))
         {
-            bfld[patchi].evaluate(commsType);
+            pfld.evaluate(commsType);
         }
     }
 }
@@ -989,32 +997,30 @@ void Foam::oversetFvMeshBase::write
 template<class GeoField>
 void Foam::oversetFvMeshBase::correctCoupledBoundaryConditions(GeoField& fld)
 {
-    typename GeoField::Boundary& bfld = fld.boundaryFieldRef();
+    auto& bfld = fld.boundaryFieldRef();
 
     const UPstream::commsTypes commsType = UPstream::defaultCommsType;
+
     const label startOfRequests = UPstream::nRequests();
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (bfld[patchi].coupled())
+        if (pfld.coupled())
         {
-            //Pout<< "initEval of " << bfld[patchi].patch().name() << endl;
-            bfld[patchi].initEvaluate(commsType);
+            //Pout<< "initEval of " << pfld.patch().name() << endl;
+            pfld.initEvaluate(commsType);
         }
     }
 
-    // Wait for outstanding requests
-    if (commsType == UPstream::commsTypes::nonBlocking)
-    {
-        Pstream::waitRequests(startOfRequests);
-    }
+    // Wait for outstanding requests (non-blocking)
+    UPstream::waitRequests(startOfRequests);
 
-    forAll(bfld, patchi)
+    for (auto& pfld : bfld)
     {
-        if (bfld[patchi].coupled())
+        if (pfld.coupled())
         {
-            //Pout<< "eval of " << bfld[patchi].patch().name() << endl;
-            bfld[patchi].evaluate(commsType);
+            //Pout<< "eval of " << pfld.patch().name() << endl;
+            pfld.evaluate(commsType);
         }
     }
 }