I am trying to reproduce the work done in this paper https://doi.org/10.1021/acscatal.7b00588. In this direction, I have been successful in optimizing the unit cells of the zeolites. For further steps, I need to extract rings having 6,8,10 members. Is there any tool available that can extract the atomic positions of these rings?

I am aware of the MAZE-sim package that is written over ASE, which is capable of extracting and manipulating "sites" but not rings.

Could someone suggest some resource (tool or code snippet) that could be used to extract such rings of different sizes from zeolite?

  • $\begingroup$ If you have optimized your crystal structure in a program like VASP, you can open its file in my program Chemcraft. It provides different tools for extracting the coordinates, for example you can select an atom and with each click Chemcraft will show you the atoms adjacent to it in the crystal. Besides that, the latest version of Chemcraft (b675) has new tools for working with crystal data, e.g. you can wrap the fractional coordinates, cleave the surface, build new crystal choosing custom ABC vectors, etc. Maybe this will be sufficient for you? $\endgroup$
    – Linkey
    Nov 7, 2023 at 18:38

3 Answers 3


While there might not be a dedicated tool that directly extracts rings of different sizes from zeolite structures, you can achieve this using graph theory and network analysis libraries that can be helpful in identifying rings in crystal structures. You can consider using tools like NetworkX (Python library) or igraph (available for various programming languages) to help analyze the connectivity of atoms in the zeolite structure.

Here is a sample code using python library networkX:

import networkx as nx

def find_rings(graph, size):
    rings = []
    for node in graph.nodes():
        for path in nx.all_simple_paths(graph, source=node, cutoff=size):
            if len(path) == size + 1 and graph.has_edge(path[-1], path[0]):
    return rings

# Load your crystal structure and create a graph
# Replace this with your actual structure loading code
# Example: Load a CIF file using ASE
from ase.io import read
zeolite_structure = read('zeolite.cif')

# Create a graph using NetworkX
G = nx.Graph()
for atom in zeolite_structure:
for bond in zeolite_structure.get_bonds():
    G.add_edge(bond.index[0], bond.index[1])

# Find rings of specific sizes
ring_size = 6  # Change this to 8 or 10 for different ring sizes
rings = find_rings(G, ring_size)

print(f"Found {len(rings)} rings of size {ring_size}")
  • $\begingroup$ Thank you @VandanRevanur for the response. The code didn't work however, despite tweaking it. The main error that I encounter is: NetworkXNotImplemented: not implemented for undirected type $\endgroup$
    – ansonthms
    Aug 31, 2023 at 13:23

R.I.N.G.S. code

The RINGS code can generate a number of ring statistics, including the number of rings (with many supported definitions). Among its multiple outputs are the list of atom indices of each ring (in rstat/liste-N). It is thoroughly described on its website and in its companion article.

If you want a python wrapper to get some rings statistics from this software, you can check the python package aMOF (disclaimer: I'm the developer).

  • $\begingroup$ Thank you @Hebo for suggesting this code. However, I am unable to open the page rings-code.sourceforge.net. Seems that the site is not working currently. aMOF did not work in my case since it did not support the zeolites I desire to study $\endgroup$
    – ansonthms
    Aug 31, 2023 at 15:04


If you prefer your rings to be returned as a python list to do further analysis with, there's code available at https://github.com/MorrowChem/RingsStatisticsMatter.jl

With a couple of lines of python (and installing Julia), you can get the nodes of the rings in your structure, e.g.

ats = read('structures/POSCAR-SiO2-a-quartz', '-1')

rs, rings = ring_statistics(ats, cutoff=1.63, maxlvl=20)



# Nodes for 12-membered rings
[array([0, 6, 2, 7, 1, 8, 0, 3, 1, 4, 2, 5], dtype=int64),
  array([0, 8, 1, 3, 0, 5, 2, 4, 1, 7, 2, 6], dtype=int64),
  array([0, 8, 1, 7, 2, 4, 1, 3, 0, 5, 2, 6], dtype=int64)])

Ring statistics:
Ring Size |            Count 
        1 |             0.0
        2 |             0.0
        3 |             0.0
        4 |             0.0
        5 |             0.0
        6 |             0.0
        7 |             0.0
        8 |             0.0
        9 |             0.0
       10 |             0.0
       11 |             0.0
       12 |             3.0
       13 |             0.0
       14 |             0.0
       15 |             0.0
       16 |            15.0
       17 |             0.0
       18 |             0.0

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .