order of dofs within a cell in a FESystem

45 views
Skip to first unread message

Praveen C

unread,
Jun 1, 2021, 5:34:11 AM6/1/21
to Deal. II Googlegroup
Is it possible to change the order of dofs within a cell in a FESystem ?

I have situation like this:

FESystem<dim> fe;

degree = 1
nvar = 4 // number of unknowns at each support point

fe(FE_DGQArbitrarynodes(QGauss<1>(degree+1), nvar)

I print

for i = 0; i<fe.dofs_per_cell; ++i

comp_i = fe.system_to_component_index(i).first
indx_i = fe.system_to_component_index(i).second

i comp_i indx_i
0 0 0
1 0 1
2 0 2
3 0 3
4 1 0
5 1 1
6 1 2
7 1 3
8 2 0
9 2 1
10 2 2
11 2 3
12 3 0
13 3 1
14 3 2
15 3 3

All

0'th component are consecutive
1'th component are consecutive
etc.

Is it possible to have the other ordering

i comp_i indx_i
0 0 0
1 1 0
2 2 0
3 3 0
4 0 1
5 1 1
6 2 1
7 3 1
8 0 2
9 1 2
10 2 2
11 3 2
12 0 3
13 1 3
14 2 3
15 3 3

Thanks
praveen

Wells, David

unread,
Jun 1, 2021, 11:12:49 AM6/1/21
to Deal. II Googlegroup
Hi Praveen,

I don't think its possible to change the internal numbering used by FESystem itself since it must support the case where not all finite elements have the same number of degrees of freedom. If you really need to accomplish this you will have to write a new finite element class. Another possibility (if all the base elements are the same) would be to only have one finite element and do the block-based numbering manually since each component will have the same number of dofs.

Best,
David

From: dea...@googlegroups.com <dea...@googlegroups.com> on behalf of Praveen C <cpra...@gmail.com>
Sent: Tuesday, June 1, 2021 5:34 AM
To: Deal. II Googlegroup <dea...@googlegroups.com>
Subject: [deal.II] order of dofs within a cell in a FESystem
 
--
The deal.II project is located at http://www.dealii.org/
For mailing list/forum options, see https://groups.google.com/d/forum/dealii?hl=en
---
You received this message because you are subscribed to the Google Groups "deal.II User Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email to dealii+un...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/dealii/CC6DB04A-6A8C-4CEE-B895-1B36D151EAFB%40gmail.com.

Praveen C

unread,
Jun 2, 2021, 12:32:08 AM6/2/21
to Deal. II Googlegroup
Thanks David for the clarification.

I am using nodal DG basis.

I would like all components located at a support point to be consecutive in memory.

I could achieve this by implementing a renumber_node_wise function.

However, when I get local dofs on a cell

cell->get_dof_indices(local_dof_indices)

the indices pointed by local_dof_indices are not consecutive in memory, since this order is fixed by FESystem.

I can make my own looping without using local_dof_indices which reads consecutively from a Vector but it would be nice if this was already supported by some FE class.

A space like

FE_DGTensor( fe_dg_1d, n_components)

where n_components are together in memory, seems very useful.

Best
praveen

Wolfgang Bangerth

unread,
Jun 2, 2021, 11:14:24 AM6/2/21
to dea...@googlegroups.com

> I would like all components located at a support point to be consecutive in
> memory.
>
> I could achieve this by implementing a *renumber_node_wise* function.
>
> However, when I get local dofs on a cell
>
> cell->get_dof_indices(local_dof_indices)
>
> the indices pointed by *local_dof_indices* are not consecutive in memory,
> since this order is fixed by FESystem.
>
> I can make my own looping without using local_dof_indices which reads
> consecutively from a Vector but it would be nice if this was already supported
> by some FE class.
>
> A space like
>
> FE_DGTensor( fe_dg_1d, n_components)
>
> where n_components are together in memory, seems very useful.

For DG, it probably wouldn't be very difficult to implement something like
this, but it doesn't exist at the moment.

Can I ask why you want this particular property? Why is it not enough to have
all DoFs associated with a cell contiguous in memory? And why do you care
about the cell-local order of DoFs, and not the global DoF indices?

Best
W.

--
------------------------------------------------------------------------
Wolfgang Bangerth email: bang...@colostate.edu
www: http://www.math.colostate.edu/~bangerth/

Praveen C

unread,
Jun 2, 2021, 11:56:53 AM6/2/21
to Deal. II Googlegroup


On 02-Jun-2021, at 8:44 PM, Wolfgang Bangerth <bang...@colostate.edu> wrote:

For DG, it probably wouldn't be very difficult to implement something like this, but it doesn't exist at the moment.

Can I ask why you want this particular property? Why is it not enough to have all DoFs associated with a cell contiguous in memory? And why do you care about the cell-local order of DoFs, and not the global DoF indices?


I do want all dofs in a cell to be contiguous in memory. But I want bit more. 

In a setup like this, say in dim=2

FESystem( FE_DGQArbitraryNodes(QGauss<1>(degree+1)), nvar)
Vector<double> solution

on each cell I want to extract the solution into a local variable 

double cell_solution[degree+1][degree+1][nvar]

So I want all nvar-values at each support point to be contiguous in memory. 

I can achieve this by doing a DoF renumbering. Suppose I have done this.

Now when I extract

cell->get_dof_indices( local_dof_indices );
index = 0;
for(j = 0; j < degree+1; ++j)
   for(i = 0; i < degree+1; ++i)
      for(c = 0; c < nvar; ++c)
      {
         cell_solution[j][i][c] = solution( local_dof_indices[index] );
         ++index;
      }

The access into solution is not contiguous, it jumps around. This is because of how FESystem orders dofs within a cell.

To access solution contiguously, I can do this

cell->get_dof_indices( local_dof_indices );
for(j = 0; j < degree+1; ++j)
   for(i = 0; i < degree+1; ++i)
      for(c = 0; c < nvar; ++c)
      {
         c_index = i + (degree+1)*j;
         index = fe.component_to_system_index(c, c_index);
         cell_solution[j][i][c] = solution( local_dof_indices[index] );
      }

but my access into local_dof_indices is not contiguous.

In a DG case, I should be able to do the following, without needing local_dof_indices, and still  access all memory contiguously

cell->get_dof_indices( local_dof_indices );
index = local_dof_indices[0]; // get first index on this cell
for(j = 0; j < degree+1; ++j)
   for(i = 0; i < degree+1; ++i)
      for(c = 0; c < nvar; ++c)
      {
         cell_solution[j][i][c] = solution( index );
         ++index;
      }

There is no need for the whole local_dof_indices, if I know the starting index on cell, it is enough.

This would be useful for writing tensor product DG codes, which is needed for things like Euler/compressible NS problems. 

Thanks
praveen

Wolfgang Bangerth

unread,
Jun 2, 2021, 12:24:35 PM6/2/21
to dea...@googlegroups.com

Praveen,

> In a setup like this, say in dim=2
>
> FESystem( FE_DGQArbitraryNodes(QGauss<1>(degree+1)), nvar)
> Vector<double> solution
>
> on each cell I want to extract the *solution* into a local variable
>
> double cell_solution[degree+1][degree+1][nvar]
>
> So I want all *nvar*-values at each support point to be contiguous in memory.
>
> I can achieve this by doing a DoF renumbering. Suppose I have done this.
>
> Now when I extract
>
> cell->get_dof_indices( local_dof_indices );
> index = 0;
> for(j = 0; j < degree+1; ++j)
> for(i = 0; i < degree+1; ++i)
> for(c = 0; c < nvar; ++c)
>       {
>          cell_solution[j][i][c] = solution( local_dof_indices[index] );
>          ++index;
>       }
>
> The access into *solution* is not contiguous, it jumps around. This is because
> of how FESystem orders dofs within a cell.
>
> To access *solution* contiguously, I can do this
>
> cell->get_dof_indices( local_dof_indices );
> for(j = 0; j < degree+1; ++j)
> for(i = 0; i < degree+1; ++i)
> for(c = 0; c < nvar; ++c)
>       {
>          c_index = i + (degree+1)*j;
>          index = fe.component_to_system_index(c, c_index);
>          cell_solution[j][i][c] = solution( local_dof_indices[index] );
>       }
>
> but my access into *local_dof_indices* is not contiguous.

Right. The question is: Does it matter? All of these accesses should be close
enough in memory that you shouldn't incur a lot of cache misses.


> In a DG case, I should be able to do the following, without needing
> *local_dof_indices*, and still  access all memory contiguously
>
> cell->get_dof_indices( local_dof_indices );
> index = local_dof_indices[0]; // get first index on this cell
> for(j = 0; j < degree+1; ++j)
> for(i = 0; i < degree+1; ++i)
> for(c = 0; c < nvar; ++c)
>       {
>          cell_solution[j][i][c] = solution( index );
>          ++index;
>       }
>
> There is no need for the whole *local_dof_indices*, if I know the starting
> index on cell, it is enough.

But you can achieve this using global DoF index renumbering. That's the way
I'd go.
Reply all
Reply to author
Forward
0 new messages