hashin_shtrikman_mp
  • Home
  • Examples
    • 3-phase Composite Example
    • Example Visualizations for 2-, 3-, and 4-phase Composites
  • Documentation
    • Genetic Algorithm
      • GeneticAlgorithmParams
      • GeneticAlgorithmResult
      • GeneticAlgorithm
      • Member
      • OptimizationParams
      • Population
    • User Input
      • Aggregate
      • MaterialProperty
      • Material
      • MixtureProperty
      • Mixture
      • UserInput
    • Visualization
      • CompositePropertyPlotter
      • OptimizationResultVisualizer
    • MatchFinder
  • Search
  • Previous
  • Next
  • Edit on Github
  • 3-phase Composite Example

3-phase Composite Example¶

In [1]:
Copied!
from hashin_shtrikman_mp.core.user_input import Aggregate, MaterialProperty, Material, MixtureProperty, Mixture, UserInput
from hashin_shtrikman_mp.core import GeneticAlgorithm
from hashin_shtrikman_mp.core.genetic_algorithm import OptimizationParams
from hashin_shtrikman_mp.core.visualization import OptimizationResultVisualizer
from hashin_shtrikman_mp.core.match_finder import MatchFinder
from IPython.display import Image
from hashin_shtrikman_mp.core.user_input import Aggregate, MaterialProperty, Material, MixtureProperty, Mixture, UserInput from hashin_shtrikman_mp.core import GeneticAlgorithm from hashin_shtrikman_mp.core.genetic_algorithm import OptimizationParams from hashin_shtrikman_mp.core.visualization import OptimizationResultVisualizer from hashin_shtrikman_mp.core.match_finder import MatchFinder from IPython.display import Image

Define properties for each material

In [2]:
Copied!
properties_mat_1 = [
    MaterialProperty(prop='elec_cond_300k_low_doping',  upper_bound=120, lower_bound=1e-7),
    MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2,   lower_bound=1e-7),
    MaterialProperty(prop='bulk_modulus',               upper_bound=500, lower_bound=50),
    MaterialProperty(prop='shear_modulus',              upper_bound=500, lower_bound=80),
    MaterialProperty(prop='universal_anisotropy',       upper_bound=6,   lower_bound=1),
]

properties_mat_2 = [
    MaterialProperty(prop='elec_cond_300k_low_doping',  upper_bound=78,  lower_bound=1e-7),
    MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2,   lower_bound=1e-7),
    MaterialProperty(prop='bulk_modulus',               upper_bound=400, lower_bound=20),
    MaterialProperty(prop='shear_modulus',              upper_bound=500, lower_bound=100),
    MaterialProperty(prop='universal_anisotropy',       upper_bound=4.3, lower_bound=1.3),
]

properties_mat_3 = [
    MaterialProperty(prop='elec_cond_300k_low_doping',  upper_bound=78,  lower_bound=1e-7),
    MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2,   lower_bound=1e-7),
    MaterialProperty(prop='bulk_modulus',               upper_bound=700, lower_bound=20),
    MaterialProperty(prop='shear_modulus',              upper_bound=600, lower_bound=100),
    MaterialProperty(prop='universal_anisotropy',       upper_bound=2.1, lower_bound=0.9),
]
properties_mat_1 = [ MaterialProperty(prop='elec_cond_300k_low_doping', upper_bound=120, lower_bound=1e-7), MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2, lower_bound=1e-7), MaterialProperty(prop='bulk_modulus', upper_bound=500, lower_bound=50), MaterialProperty(prop='shear_modulus', upper_bound=500, lower_bound=80), MaterialProperty(prop='universal_anisotropy', upper_bound=6, lower_bound=1), ] properties_mat_2 = [ MaterialProperty(prop='elec_cond_300k_low_doping', upper_bound=78, lower_bound=1e-7), MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2, lower_bound=1e-7), MaterialProperty(prop='bulk_modulus', upper_bound=400, lower_bound=20), MaterialProperty(prop='shear_modulus', upper_bound=500, lower_bound=100), MaterialProperty(prop='universal_anisotropy', upper_bound=4.3, lower_bound=1.3), ] properties_mat_3 = [ MaterialProperty(prop='elec_cond_300k_low_doping', upper_bound=78, lower_bound=1e-7), MaterialProperty(prop='therm_cond_300k_low_doping', upper_bound=2, lower_bound=1e-7), MaterialProperty(prop='bulk_modulus', upper_bound=700, lower_bound=20), MaterialProperty(prop='shear_modulus', upper_bound=600, lower_bound=100), MaterialProperty(prop='universal_anisotropy', upper_bound=2.1, lower_bound=0.9), ]

Create an instance of the Material class for each material

In [3]:
Copied!
mat_1   = Material(name='mat_1', properties=properties_mat_1)
mat_2   = Material(name='mat_2', properties=properties_mat_2)
mat_3   = Material(name='mat_3', properties=properties_mat_3)
mat_1 = Material(name='mat_1', properties=properties_mat_1) mat_2 = Material(name='mat_2', properties=properties_mat_2) mat_3 = Material(name='mat_3', properties=properties_mat_3)

Define properties for the mixture

In [4]:
Copied!
properties_mixture = [
    MixtureProperty(prop='elec_cond_300k_low_doping',  desired_prop=9),
    MixtureProperty(prop='therm_cond_300k_low_doping', desired_prop=0.9),
    MixtureProperty(prop='bulk_modulus',               desired_prop=280),
    MixtureProperty(prop='shear_modulus',              desired_prop=230),
    MixtureProperty(prop='universal_anisotropy',       desired_prop=1.5),
]
properties_mixture = [ MixtureProperty(prop='elec_cond_300k_low_doping', desired_prop=9), MixtureProperty(prop='therm_cond_300k_low_doping', desired_prop=0.9), MixtureProperty(prop='bulk_modulus', desired_prop=280), MixtureProperty(prop='shear_modulus', desired_prop=230), MixtureProperty(prop='universal_anisotropy', desired_prop=1.5), ]

Create an instance of the Mixture class to store the desired composite properties and aggregate the materials and mixture into a list for later iteration

In [5]:
Copied!
mixture = Mixture(name='mixture', properties=properties_mixture)
mixture = Mixture(name='mixture', properties=properties_mixture)

Create an instance of the Aggregate class which aggregates the material property search bounds across materials to find the maximum upper bound per property and minimum lower bound per property.

Then call get_bounds_dict to store the search bounds in a dictionary for use when finding real material matches in the Materials Project database.

In [6]:
Copied!
aggregate = Aggregate(name='aggregate', components=[mat_1, mat_2, mat_3, mixture])
bounds_dict = aggregate.get_bounds_dict()
aggregate = Aggregate(name='aggregate', components=[mat_1, mat_2, mat_3, mixture]) bounds_dict = aggregate.get_bounds_dict()

Create an instance of the UserInput class from the materials and mixture(s) just created

In [7]:
Copied!
user_input= UserInput(materials=[mat_1, mat_2, mat_3], mixtures=[mixture])
user_input= UserInput(materials=[mat_1, mat_2, mat_3], mixtures=[mixture])

Initialize an instance of the OptimizationParams class using the previously defined UserInput, as well as an instance of the GeneticAlgorithm class

In [8]:
Copied!
optimization_parameters = OptimizationParams.from_user_input(user_input)
ga = GeneticAlgorithm()
optimization_parameters = OptimizationParams.from_user_input(user_input) ga = GeneticAlgorithm()

Run the optimization $n=3$ materials. Identify the optimal properties of each material and the respective volume fractions that achieve the desired composite material properties.

In [9]:
Copied!
ga_result = ga.run(user_input, gen_counter=False)
ga_result = ga.run(user_input, gen_counter=False)

Create an instance of the OptimizationResultVisualizer class using the genetic algorithm result

In [10]:
Copied!
visualizer = OptimizationResultVisualizer(ga_result)
visualizer = OptimizationResultVisualizer(ga_result)

Print the optimization results as a table. Each row represents a theoretical material.

In [11]:
Copied!
visualizer.print_table_of_best_designs(rows=10)
visualizer.print_table_of_best_designs(rows=10)

Plot the genetic algorithm convergence plot

In [12]:
Copied!
visualizer.plot_optimization_results()
visualizer.plot_optimization_results()
convg

Plot the contributions to the cost function for the best performer

Note on how many contributions to expect: Per property, there is

  • 1 effective property term
  • (Non-modulus) 2 concentration factor terms per material
  • (Modulus) 2 concentration factor terms per coupled (bulk, shear) moduli per material -- not considered individual properties

For example, for a 3-phase composite which considers carrier-transport and elastic property categories, not including volume fraction, there are 5 properties per material, so in total we expect

  • 5 effective property terms
  • 18 = 6 concentration factor terms (load and response terms for electrical conductivity, thermal conductivity, and universal anisotropy) $\times$ 3 materials
  • 6 = 2 concentration factor terms (coupled deviatoric and hydrostatic terms from coupled bulk/shear moduli) $\times$ 3 materials
In [13]:
Copied!
visualizer.plot_cost_func_contribs()
visualizer.plot_cost_func_contribs()
Cost: 0.04477574762468891, Number effective properties: 5, Number of concentration factors: 24
cost-func-contribs

Create an instance of the MatchFinder class using the genetic algorithm result

In [14]:
Copied!
match_finder = MatchFinder(ga_result)
match_finder = MatchFinder(ga_result)

Finally, get real material matches

In [15]:
Copied!
matches_dict = match_finder.get_material_matches(bounds_dict)
matches_dict = match_finder.get_material_matches(bounds_dict)
Retrieving SummaryDoc documents:   0%|          | 0/261 [00:00<?, ?it/s]

Let's take a peak at the matches that were returned

In [16]:
Copied!
print(f'Material Matches:')

for mat in matches_dict.keys():
    print(f'  For {mat}:')
    for match_dict in matches_dict[mat]:
        for mpid in match_dict.keys():
            print(f'    {mpid}')
print(f'Material Matches:') for mat in matches_dict.keys(): print(f' For {mat}:') for match_dict in matches_dict[mat]: for mpid in match_dict.keys(): print(f' {mpid}')
Material Matches:
  For mat1:
    mp-684591
    mp-752826
    mp-3098
    mp-3748
    mp-3536
    mp-4391
    mp-5924
    mp-753459
    mp-2657
    mp-755759
    mp-4820
  For mat2:
    mp-684591
    mp-752826
    mp-3098
    mp-3748
    mp-3536
    mp-4391
    mp-5924
    mp-753459
    mp-2657
    mp-755759
    mp-4820
  For mat3:
    mp-684591
    mp-752826
    mp-3098
    mp-3748
    mp-3536
    mp-4391
    mp-5924
    mp-753459
    mp-2657
    mp-755759
    mp-4820

If the above cell fails, the Materials Project API may have been updated. Uncomment and run the following cell and then re-run the entire notebook.

In [17]:
Copied!
#!pip install --upgrade mp-api
#!pip install --upgrade mp-api

An extra note: For reading bulk and shear moduli from the Materials Project database, there are a few options outlined here. In hashin_shtrikman_mp we use the Voigt-Reuss-Hill average.


Built by Carla Becker, Hrushikesh Sahasrabuddhe, and Max C. Gallant

Documentation built with MkDocs.

Search

From here you can search these documents. Enter your search terms below.

Keyboard Shortcuts

Keys Action
? Open this help
n Next page
p Previous page
s Search