Skip to content

Commit a9f047c

Browse files
committed
Add driver based on external LBFGS implementation
1 parent e0ad1a9 commit a9f047c

File tree

9 files changed

+280
-25
lines changed

9 files changed

+280
-25
lines changed

CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ cmake_policy(SET CMP0074 NEW)
44

55
project (MGmol C CXX Fortran)
66

7-
set (CMAKE_CXX_STANDARD 11)
7+
set (CMAKE_CXX_STANDARD 14)
88

99
# Specify the location of additional CMAKE modules
1010
SET(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake_modules)

drivers/CMakeLists.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,14 @@ add_executable(check_input check_input.cc)
44

55
add_executable(example1 example1.cc)
66

7+
add_executable(lbfgspp lbfgspp.cc)
8+
79
target_include_directories(check_input PRIVATE ${Boost_INCLUDE_DIRS})
810
target_include_directories(example1 PRIVATE ${Boost_INCLUDE_DIRS})
11+
target_include_directories(lbfgspp PRIVATE ${Boost_INCLUDE_DIRS})
12+
target_include_directories(lbfgspp PRIVATE /home/q8j/GIT/eigen)
13+
target_include_directories(lbfgspp PRIVATE /home/q8j/GIT/LBFGSpp/include)
914

1015
target_link_libraries(check_input mgmol_src)
1116
target_link_libraries(example1 mgmol_src)
17+
target_link_libraries(lbfgspp mgmol_src)

drivers/lbfgspp.cc

Lines changed: 249 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,249 @@
1+
// Copyright (c) 2017, Lawrence Livermore National Security, LLC and
2+
// UT-Battelle, LLC.
3+
// Produced at the Lawrence Livermore National Laboratory and the Oak Ridge
4+
// National Laboratory.
5+
// LLNL-CODE-743438
6+
// All rights reserved.
7+
// This file is part of MGmol. For details, see https://github.com/llnl/mgmol.
8+
// Please also read this link https://github.com/llnl/mgmol/LICENSE
9+
10+
// This driver uses the header-only LBFGS++ library
11+
// https://github.com/yixuan/LBFGSpp
12+
13+
#include <Eigen/Core>
14+
#include <LBFGS.h>
15+
#include <iostream>
16+
17+
#include "Control.h"
18+
#include "ExtendedGridOrbitals.h"
19+
#include "LocGridOrbitals.h"
20+
#include "MGmol.h"
21+
#include "MGmol_MPI.h"
22+
#include "MPIdata.h"
23+
#include "mgmol_run.h"
24+
25+
#include <cassert>
26+
#include <iostream>
27+
#include <time.h>
28+
#include <vector>
29+
30+
#include <boost/program_options.hpp>
31+
namespace po = boost::program_options;
32+
33+
using Eigen::VectorXd;
34+
35+
class MGmolEnergyAndForces
36+
{
37+
private:
38+
MGmolInterface* mgmol_;
39+
int n_;
40+
std::vector<short>& anumbers_;
41+
42+
public:
43+
MGmolEnergyAndForces(
44+
MGmolInterface* mgmol, const int n, std::vector<short>& anumbers)
45+
: mgmol_(mgmol), n_(n), anumbers_(anumbers)
46+
{
47+
}
48+
49+
double operator()(const VectorXd& x, VectorXd& grad)
50+
{
51+
std::vector<double> positions(n_);
52+
for (int i = 0; i < n_; i++)
53+
{
54+
positions[i] = x[i];
55+
}
56+
if (MPIdata::onpe0)
57+
{
58+
std::cout << "Positions:" << std::endl;
59+
for (std::vector<double>::iterator it = positions.begin();
60+
it != positions.end(); it += 3)
61+
{
62+
for (int i = 0; i < 3; i++)
63+
std::cout << " " << *(it + i);
64+
std::cout << std::endl;
65+
}
66+
}
67+
68+
// compute energy and forces using all MPI tasks
69+
// expect positions to be replicated on all MPI tasks
70+
std::vector<double> forces(n_);
71+
double fx
72+
= mgmol_->evaluateEnergyAndForces(positions, anumbers_, forces);
73+
// print out results
74+
if (MPIdata::onpe0)
75+
{
76+
std::cout << "Energy: " << fx << std::endl;
77+
std::cout << "Forces:" << std::endl;
78+
for (std::vector<double>::iterator it = forces.begin();
79+
it != forces.end(); it += 3)
80+
{
81+
double norm = 0.;
82+
for (int i = 0; i < 3; i++)
83+
{
84+
double val = *(it + i);
85+
std::cout << " " << val;
86+
norm += val * val;
87+
}
88+
std::cout << " norm: " << std::sqrt(norm);
89+
std::cout << std::endl;
90+
}
91+
}
92+
93+
// set gradient to negative forces
94+
for (int i = 0; i < n_; i++)
95+
{
96+
grad[i] = -1. * forces[i];
97+
}
98+
return fx;
99+
}
100+
};
101+
102+
int main(int argc, char** argv)
103+
{
104+
int mpirc = MPI_Init(&argc, &argv);
105+
if (mpirc != MPI_SUCCESS)
106+
{
107+
std::cerr << "MPI Initialization failed!!!" << std::endl;
108+
MPI_Abort(MPI_COMM_WORLD, 0);
109+
}
110+
111+
MPI_Comm comm = MPI_COMM_WORLD;
112+
113+
/*
114+
* Initialize general things, like magma, openmp, IO, ...
115+
*/
116+
mgmol_init(comm);
117+
118+
/*
119+
* read runtime parameters
120+
*/
121+
std::string input_filename("");
122+
std::string lrs_filename;
123+
std::string constraints_filename("");
124+
125+
float total_spin = 0.;
126+
bool with_spin = false;
127+
128+
po::variables_map vm;
129+
130+
// read from PE0 only
131+
if (MPIdata::onpe0)
132+
{
133+
read_config(argc, argv, vm, input_filename, lrs_filename,
134+
constraints_filename, total_spin, with_spin);
135+
}
136+
137+
MGmol_MPI::setup(comm, std::cout, with_spin);
138+
MGmol_MPI& mmpi = *(MGmol_MPI::instance());
139+
MPI_Comm global_comm = mmpi.commGlobal();
140+
141+
/*
142+
* Setup control struct with run time parameters
143+
*/
144+
Control::setup(global_comm, with_spin, total_spin);
145+
Control& ct = *(Control::instance());
146+
147+
ct.setOptions(vm);
148+
149+
int ret = ct.checkOptions();
150+
if (ret < 0) return ret;
151+
152+
mmpi.bcastGlobal(input_filename);
153+
mmpi.bcastGlobal(lrs_filename);
154+
155+
// Enter main scope
156+
{
157+
if (MPIdata::onpe0)
158+
{
159+
std::cout << "-------------------------" << std::endl;
160+
std::cout << "Construct MGmol object..." << std::endl;
161+
std::cout << "-------------------------" << std::endl;
162+
}
163+
164+
MGmolInterface* mgmol;
165+
if (ct.isLocMode())
166+
mgmol = new MGmol<LocGridOrbitals>(global_comm, *MPIdata::sout,
167+
input_filename, lrs_filename, constraints_filename);
168+
else
169+
mgmol = new MGmol<ExtendedGridOrbitals>(global_comm, *MPIdata::sout,
170+
input_filename, lrs_filename, constraints_filename);
171+
172+
if (MPIdata::onpe0)
173+
{
174+
std::cout << "-------------------------" << std::endl;
175+
std::cout << "MGmol setup..." << std::endl;
176+
std::cout << "-------------------------" << std::endl;
177+
}
178+
mgmol->setup();
179+
180+
if (MPIdata::onpe0)
181+
{
182+
std::cout << "-------------------------" << std::endl;
183+
std::cout << "Setup done..." << std::endl;
184+
std::cout << "-------------------------" << std::endl;
185+
}
186+
187+
// here we just use the atomic positions read in and used
188+
// to initialize MGmol
189+
std::vector<double> positions;
190+
mgmol->getAtomicPositions(positions);
191+
std::vector<short> anumbers;
192+
mgmol->getAtomicNumbers(anumbers);
193+
if (MPIdata::onpe0)
194+
{
195+
std::cout << "Positions:" << std::endl;
196+
std::vector<short>::iterator ita = anumbers.begin();
197+
for (std::vector<double>::iterator it = positions.begin();
198+
it != positions.end(); it += 3)
199+
{
200+
std::cout << *ita;
201+
for (int i = 0; i < 3; i++)
202+
std::cout << " " << *(it + i);
203+
std::cout << std::endl;
204+
ita++;
205+
}
206+
}
207+
208+
// Set up parameters
209+
LBFGSpp::LBFGSParam<double> param;
210+
param.epsilon = 4e-4;
211+
param.max_iterations = 100;
212+
213+
// Create solver and function object
214+
LBFGSpp::LBFGSSolver<double> solver(param);
215+
const int n = positions.size();
216+
if (MPIdata::onpe0) std::cout << "n = " << n << std::endl;
217+
MGmolEnergyAndForces fun(mgmol, n, anumbers);
218+
219+
// initial guess
220+
VectorXd x = VectorXd::Zero(n);
221+
int i = 0;
222+
for (auto& pos : positions)
223+
{
224+
x[i++] = pos;
225+
}
226+
227+
double eks;
228+
int niter = solver.minimize(fun, x, eks);
229+
230+
std::cout << niter << " iterations" << std::endl;
231+
232+
delete mgmol;
233+
234+
} // close main scope
235+
236+
mgmol_finalize();
237+
238+
mpirc = MPI_Finalize();
239+
if (mpirc != MPI_SUCCESS)
240+
{
241+
std::cerr << "MPI Finalize failed!!!" << std::endl;
242+
}
243+
244+
time_t tt;
245+
time(&tt);
246+
if (onpe0) std::cout << " Run ended at " << ctime(&tt) << std::endl;
247+
248+
return 0;
249+
}

src/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ set(SOURCES
6868
GrassmanLineMinimization.cc
6969
GrassmanCG.cc
7070
GrassmanCGSparse.cc
71-
LBFGS.cc
71+
MGmolLBFGS.cc
7272
IonicStepper.cc
7373
Energy.cc
7474
GramMatrix.cc

src/MGmol.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,12 +37,12 @@
3737
#include "Hamiltonian.h"
3838
#include "Ions.h"
3939
#include "KBPsiMatrixSparse.h"
40-
#include "LBFGS.h"
4140
#include "LocGridOrbitals.h"
4241
#include "LocalizationRegions.h"
4342
#include "MDfiles.h"
4443
#include "MGkernels.h"
4544
#include "MGmol.h"
45+
#include "MGmolLBFGS.h"
4646
#include "MLWFTransform.h"
4747
#include "MPIdata.h"
4848
#include "MasksSet.h"

0 commit comments

Comments
 (0)