def METHOD_NAME():
    vm = VonMises(tensor(0.0), tensor(1.0))
    hn = HalfNormal(tensor(0.8))
    b = Beta(tensor(2.0), tensor(5.0))
    while True:
        locs = vm.sample((2,))
        conc = hn.sample((2,))
        corr = b.sample()
        if torch.prod(conc, dim=-1) >= corr**2:
            break
    def mle_model(data):
        phi_loc = pyro.param("phi_loc", tensor(0.0), constraints.real)
        psi_loc = pyro.param("psi_loc", tensor(0.0), constraints.real)
        phi_conc = pyro.param("phi_conc", tensor(1.0), constraints.positive)
        psi_conc = pyro.param("psi_conc", tensor(1.0), constraints.positive)
        corr = pyro.param("corr", tensor(0.5), constraints.real)
        with pyro.plate("data", data.size(-2)):
            pyro.sample(
                "obs",
                SineBivariateVonMises(phi_loc, psi_loc, phi_conc, psi_conc, corr),
                obs=data,
            )
    def guide(data):
        pass
    bmv = SineBivariateVonMises(locs[0], locs[1], conc[0], conc[1], corr)
    data = bmv.sample((10_000,))
    pyro.clear_param_store()
    adam = pyro.optim.Adam({"lr": 0.01})
    svi = SVI(mle_model, guide, adam, loss=Trace_ELBO())
    losses = []
    steps = 200
    for step in range(steps):
        losses.append(svi.step(data))
    expected = {
        "phi_loc": locs[0],
        "psi_loc": locs[1],
        "phi_conc": conc[0],
        "psi_conc": conc[1],
        "corr": corr,
    }
    actuals = {k: v for k, v in pyro.get_param_store().items()}
    for k in expected.keys():
        if k in actuals:
            actual = actuals[k]
        else:
            actual = (
                actuals["corr_weight"] * actuals["phi_conc"] * actuals["psi_conc"]
            )  # k == 'corr'
        assert_equal(expected[k].squeeze(), actual.squeeze(), 9e-2)