def testRepAndKpts(self):
        def dummy(t):
            target1 = 40.0 / (t[0][0] * t[1][0])
            target1 += 10.0 / t[0][0]
            target2 = 10.0 / t[0][1]
            target3 = 10.0 / (t[0][2] * t[1][2])
            target4 = 50000 / t[2]

            return target1 + target2 + target3 + target4

        def isConverged(t, old_t):
            return (abs(dummy(t) - dummy(old_t))) / 1

        def generator(group):
            return (group["size"].repetition(), group["size"].kpts(), group["extra"].value())

        converger = Converger(
            isConverged,
            generator,
            None,
            RepetionAndKptsGroup("size", (2, 2, 1)),
            PositiveFloatParameter("extra", 5000.0, improvement_factor=2),
        )
        converger.run()

        self.assertEqual(converger["size"].kpts(), (4, 1, 2))
        self.assertEqual(converger["size"].repetition(), (5, 3, 2))
    def testEMT(self):
        def isConverged(structures, old_structures):
            differences = []
            for s1, s2 in [structures, old_structures]:
                diff = s1.get_total_energy() - s2.get_total_energy()
                differences.append(diff)
            value = abs(differences[0] - differences[1]) / 0.01
            return value

        def generator(group):
            structures = []
            for position in ["ontop", "bridge"]:
                slab = fcc111("Au", size=group["repeats"].value(), vacuum=10.0)
                add_adsorbate(slab, "Au", 3, position=position)
                slab = fixBelow(slab, slab.positions[:, 2].min() + 1e-2)
                slab.set_calculator(EMT())
                structures.append(slab)

            return structures

        converger = Converger(isConverged, generator, None, KptsGroup("repeats", (1, 1, 1)))

        converger.run()
        structures = converger.generate()