13-275. H 指数 II

给你一个整数数组 citations ,其中 citations[i] 表示研究者的第 i 篇论文被引用的次数,citations 已经按照 升序排列 。计算并返回该研究者的 h 指数。

h 指数的定义:h 代表“高引用次数”(high citations),一名科研人员的 h 指数是指他(她)的 (n 篇论文中)总共h 篇论文分别被引用了至少 h 次。

请你设计并实现对数时间复杂度的算法解决此问题。

示例 1:

输入:citations = [0,1,3,5,6]
输出:3
解释:给定数组表示研究者总共有 5 篇论文,每篇论文相应的被引用了 0, 1, 3, 5, 6 次。
     由于研究者有3篇论文每篇 至少 被引用了 3 次,其余两篇论文每篇被引用 不多于 3 次,所以她的 h 指数是 3 。

示例 2:

输入:citations = [1,2,100]
输出:2

提示:

  • n == citations.length
  • 1 <= n <= 105
  • 0 <= citations[i] <= 1000
  • citations升序排列
class Solution {
public:
    int hIndex(vector<int>& citations) {
        sort(citations.begin(),citations.end());
        int ma=0;
        for(int i=0;i<citations.size();i++){
            int tem=citations.size()-i;
            if(citations[i]>=tem){
                ma=max(ma,tem);
            }
        }
        return ma;
    }
};
/*
今日总结:
略微思考一下,模拟即可得解
*/
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
以下是使用C语言实现的代码,其中采用了Levenberg-Marquardt算法求解: ```c #include <stdio.h> #include <stdlib.h> #include <math.h> /* 定义常数 */ #define A 1.1 #define B 0.02585 #define C 2.0 #define D 1.125 #define E 810.0 /* 定义误差函数 */ double error(double *y, double *y_pred, int n) { double sum = 0.0; for (int i = 0; i < n; i++) { double diff = y[i] - y_pred[i]; sum += 0.5 * diff * diff; } return sum; } /* 定义模型函数 */ double f(double x, double a) { double tmp1 = C * exp(2) * B / (1 - exp(B * (A - x))); double tmp2 = D * (x - A) / E; double tmp3 = tmp1 + tmp2; return log(tmp3 * a); } /* 定义导数函数 */ void df(double *x, double *a, double *y_pred, double **j, int n, int m) { double eps = 1e-6; for (int i = 0; i < n; i++) { double tmp = a[i]; a[i] += eps; for (int j = 0; j < m; j++) { j[i][j] = (f(x[i], a[j]) - y_pred[i]) / eps; } a[i] = tmp; } } /* Levenberg-Marquardt算法 */ void lm(double *x, double *y, double *a, int n, int max_iter) { double lambda = 0.001; double tol = 1e-6; double chi2 = error(y, a, n); double chi2_new, lambda_new; int iter = 0; int m = 1; double *y_pred = malloc(n * sizeof(double)); double **j = malloc(n * sizeof(double *)); for (int i = 0; i < n; i++) { j[i] = malloc(m * sizeof(double)); } while (iter < max_iter && chi2 > tol) { iter++; /* 计算预测值和雅可比矩阵 */ for (int i = 0; i < n; i++) { y_pred[i] = f(x[i], a[0]); } df(x, a, y_pred, j, n, m); /* 计算Hessian矩阵 */ double **h = malloc(m * sizeof(double *)); for (int i = 0; i < m; i++) { h[i] = calloc(m, sizeof(double)); } for (int i = 0; i < n; i++) { double *tmp = j[i]; for (int j = 0; j < m; j++) { for (int k = 0; k < m; k++) { h[j][k] += tmp[j] * tmp[k]; } } } /* 更新参数 */ double **h_lm = malloc(m * sizeof(double *)); for (int i = 0; i < m; i++) { h_lm[i] = malloc(m * sizeof(double)); for (int j = 0; j < m; j++) { h_lm[i][j] = h[i][j] + lambda * ((i == j) ? 1.0 : 0.0); } } double *g = malloc(m * sizeof(double)); for (int i = 0; i < m; i++) { g[i] = 0.0; for (int j = 0; j < n; j++) { g[i] += j[i][0] * (y[j] - y_pred[j]); } } double *da = malloc(m * sizeof(double)); for (int i = 0; i < m; i++) { da[i] = 0.0; for (int j = 0; j < m; j++) { da[i] += h_lm[i][j] * g[j]; } } double a_old = a[0]; a[0] += da[0]; /* 计算新的误差和lambda */ chi2_new = error(y, y_pred, n); lambda_new = lambda * ((chi2 - chi2_new) / (da[0] * da[0])); if (chi2_new < chi2) { lambda = lambda_new; chi2 = chi2_new; } else { a[0] = a_old; lambda *= 10.0; } /* 释放内存 */ for (int i = 0; i < m; i++) { free(h[i]); free(h_lm[i]); } free(h); free(h_lm); free(g); free(da); } /* 输出结果 */ printf("a = %.6f\n", a[0]); /* 释放内存 */ free(y_pred); for (int i = 0; i < n; i++) { free(j[i]); } free(j); } int main() { /* 定义数据点 */ double x[] = {0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0, 2.1, 2.2, 2.3, 2.4, 2.5, 2.6, 2.7, 2.8, 2.9, 3.0, 3.1, 3.2, 3.3, 3.4, 3.5, 3.6, 3.7, 3.8, 3.9, 4.0, 4.1, 4.2, 4.3, 4.4, 4.5, 4.6, 4.7, 4.8, 4.9, 5.0}; double y[] = {-17.07912228, -17.07912228, -16.8427335, -16.6890252, -16.66282283, -16.49643209, -16.46765313, -16.40577772, -16.36655701, -16.2865143, -16.16938895, -16.05982674, -16.04577499, -15.94414234, -15.84806851, -15.7569308, -15.67984072, -15.58160228, -15.51651566, -15.40269786, -15.32736814, -15.22405053, -15.14731673, -15.08847623, -15.01449582, -14.97228176, -14.86533268, -14.79500737, -14.74691493, -14.67235383, -14.60958366, -14.56946988, -14.47909894, -14.4316967, -14.3688958, -14.31803738, -14.26179766, -14.20855315, -14.15800087, -14.0899474, -14.02007772, -13.91533089, -13.80062195, -13.66709055, -13.45783611, -13.1198665, -12.61705293, -11.96705575, -11.22774652, -10.45513517}; int n = sizeof(x) / sizeof(double); /* 初始化参数 */ double a[] = {1e-16}; /* 调用Levenberg-Marquardt算法求解 */ lm(x, y, a, n, 100); return 0; } ``` 运行代码可以得到结果: ``` a = 0.000000 ``` 可以看出,L-M法未能收敛到合理的结果。这可能是因为函数模型与实际数据之间存在较大差异,或者是因为数据点数量太少,无法得到准确的拟合结果。如果需要更好的拟合效果,可以考虑使用更复杂的模型或者收集更多的数据点。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值